1

I have a page that displays a calendar into with a attribute "data-date" that as a date like: "11/29/2014" and I need to check server if there's a log file for that date and change css for that div on mouse hover.

So far i get this code:

$(document).ready(function() {
  var lab = $( ".label.day" ).hover(
    function() {    
      dd = $(this).attr("data-date").split("/");
      ddo = $(this).attr("data-date");
      dday = ("0" + (dd[1])).slice(-2);
      dmonth = ("0" + (dd[0])).slice(-2);
      dyear = dd[2];
      url = "logs/log." + dyear + "-" + dmonth + "-" + dday;
      $.ajax({
        type: 'HEAD',
        url: url,
        error: function(xhr, status, error) {
          console.log(status)
        },
        success: function(xhr, status, error) {
          console.log(status)
        }
      });
      $(document).ajaxError(function(event, jqxhr, settings, thrownError) {
        console.log(thrownError)
        if ( thrownError == "Not Found" ) {
          $(".label.day").filter(ddo).addClass( "error" );
        }
      });
    }, function() {
      $(".label.day").filter(ddo).addClass( "noerror" );
    }
  );
});
<div data-date="1/16/2014" class="label day " original-title="Quinta" style="display: block;">16</div>

I can't change the class for the individual , without the .filter it changes all and .attr("data-date") doesn't work also.

Terry
  • 63,248
  • 15
  • 96
  • 118

1 Answers1

0

There are several issues with your script:

  1. You are not passing any data to the URL specified, via the data object in the $.ajax() function. Also, you need to specify to expected type of data (dataType) received (is it in JSON, plain text or otherwise?).
  2. Use deferred objects and promises to check the status of the AJAX call
  3. Use context, i.e. $(this), in your hover function so you can dictate which elements to modify without doing any filtering.
  4. HEAD is an invalid value for the type object in the AJAX call. You should use POST or GET instead, depending on how the destination script is written to handle incoming data. Here's a good guide to deciding between the two.
  5. Listen to mouseover instead of hover, as you are adding classes based on the status of the AJAX request, not the toggling between mouseover and mouseout events.
  6. Use var when declaring functions to contain/restrict them within the function's scope, otherwise you risk polluting global variables :)

An improved code is as follow, but might not work unless you furnish more details on how you're checking the server for information.

$(document).ready(function() {
    $('.label.day').on('mouseover', function() {
        // Cache $(this)
        var $t = $(this);

        // Reset class
        $t.removeClass('error noerror');

        // Declare variables within function scope (not global)
        var dd = $t.attr("data-date").split("/"),
            ddo = $t.attr("data-date"),
            dday = ("0" + (dd[1])).slice(-2),
            dmonth = ("0" + (dd[0])).slice(-2),
            dyear = dd[2],
            url = "logs/log." + dyear + "-" + dmonth + "-" + dday;

        // Perform AJAX call
        var $check = $.ajax({
            type: 'POST', //or "GET"
            url: url;
        });

        // jQuery deferred object
        $check.fail(function(jqXHR, textStatus) {
            // If AJAX request failed and returned an error
            console.log(textStatus);
            $t.addClass('error');

        }).done(function(data) {
            // If AJAX request is successful
            console.log(data);
            $t.addClass('noerror');
        });

    });
});
Community
  • 1
  • 1
Terry
  • 63,248
  • 15
  • 96
  • 118
  • Thks for the tips, in fact I used HEAD because I don't need a sucess answer, I'm only checking for status error. So it changes the class (color change), but it still doesn't change that class. – Filipe Silva Nov 28 '14 at 16:52
  • If you're simply checking a status, then use `GET`. That is what it's designed for. Anyway, what do you mean by "doesn't change that class"? In light that users might hover in and out an element repeatedly, you should call `.removeClass('error noerror')` at the beginning ;) Also realized that `.hover()` is likely not the right function — if you want to add classes conditionally based on AJAX request, just listen to `mouseover` and perform the logic in the `.done()` or `.fail()` deferred objects. – Terry Nov 28 '14 at 17:04
  • Thx Terry, you're right, i need to call .removeClass('error noerror'), I didn't get it to add the class anyway. – Filipe Silva Nov 28 '14 at 19:03
  • Terry, atm everything works fine, but it doesn't recognise $(this).addClass('noerror'); and $(this).addClass('error'); I'll give you the full [link](http://bitaite.tk) – Filipe Silva Nov 28 '14 at 19:24
  • @FilipeSilva I apologize — the `$(this)` in the jQuery deferred object wasn't referring to the link, that's why. Fixed the issue now, see updated answer ;) – Terry Nov 28 '14 at 22:03
  • that solve my problem, I get back to the HEAD solution, because after a few tests, it's faster then a GET or POST option. also the .removeClass I did to the full
    cause of the delay between mouseover and mouseout
    – Filipe Silva Nov 28 '14 at 22:42