0

I'm working on a dynamic calendar that allows user to click on individual days to change whether they're available or unavailable. It works as it's supposed to up until I select another month or year. Once that happens the "click" event on individual cells/days doesn't work.

// Changes cell background of the calendar
var changeColor = function(temp) {
// if cell background is white -> change to green
if(temp.css('background-color') == "rgba(0, 0, 0, 0)") {
    temp.css('background-color', 'green');
    // if cell background is green -> change to red
} else if (temp.css('background-color') == "rgb(0, 128, 0)") {
    temp.css('background-color', 'red');
} else {
    // else change back to white
    temp.css('background-color', '');
}
};

Here is were it's used

$(document).ready(function() {
// When a date-cell is clicked - changes color to green -> red -> white
$(".calCell:not(.empty)").click(function() {
    changeColor($(this));
});

});

The two buttons that change the whole calendar to red or green seem to work fine with each month selected.

// When Available button is click -> changes whole calendar to available
$("#yes").on("click", function() {
    $(".calCell:not(.empty)").css('background-color', 'green');
});

// When Unavailable button is clicked -> changes whole calendar to unavailable
$("#no").on("click", function() {
    $(".calCell:not(.empty)").css('background-color', 'red');
});

Example: JS Fiddle

Gorgon_Union
  • 563
  • 2
  • 8
  • 24

3 Answers3

0

You can use on() instead of click().

I assumed that on your implementation, when another month/year is selected the view changes. The problem is that click() binding will only attach the handler to already existing elements, that's why it will not work when you changed the views dynamically.

Use this instead:

$(".calCell:not(.empty)").on("click", function(){
    changeColor($(this));
});
Severino Lorilla Jr.
  • 1,637
  • 4
  • 20
  • 33
  • Unfortunately doesn't work. The problem still persist. The two buttons that change the whole calendar to 'Available' or 'Unavailable' seem to work with each month. It's just the individual days. – Gorgon_Union Apr 19 '16 at 02:04
  • 1
    You need to use the delegation syntax of `.on()` for dynamically-added elements. – Barmar Apr 19 '16 at 02:50
0

Your click handler is firing. I verified it by putting a console.log() in that click event. The problem is with the changeColor function.

Weirdly, your fiddle worked fine for me in Chrome, but wasn't in Firefox. In your changeColor function, you're checking the value of background-color which was never set in your CSS. First step is to add background-color: white; to your .calCell style rule.

Second, you'll have to update your changeColor function to check for the correct color. Currently, your first check is:

if(temp.css('background-color') == "rgba(0, 0, 0, 0)")

Which is a check for the color black, not white, with no opacity. Since you're not taking advantage of opacity in your colors, I'd suggest just checking the rgb rather than rgba, by updating the check to:

if(temp.css('background-color') == "rgb(255, 255, 255)")

Once you've set an initial value for the background-color and updated your check to match on the correct color, this should work across browsers

Jonathan Michalik
  • 1,492
  • 14
  • 15
0

The problem here is you are reloading the DOM. That is why the attached event to it loses. You have to reattach the event to it. Just like this ...

I put your click event inside displayCalGrid function.. So whenever the cells was created .. It will attach the event to it.

var displayCalGrid = function(mnth, yr) {

    var firstDayOfMonth = mnth + "/1/" + yr;
    var d = new Date(firstDayOfMonth);
    var numOfDaysInMonth = daysInMonth(d);
    var firstDayOfWeek = d.getDay();
    var calstr = "";

    $("#results").html("");

    for(var j = 0; j < firstDayOfWeek; j++){
        calstr += "<div class='calCell empty'></div>";
    }

    var maxCalDays = 35;
    for(var i =0; i<numOfDaysInMonth; i++) {
        // if there are 7 cells create string - row
        if((i+ firstDayOfWeek) %7 ==0 && i>0) {
            calstr += "<div class='row'>";
        }


        // increments through each cell - making up each row
        calstr += "<div class='calCell'>" + (i+1) + "</div>";
        if (i%7 ==0 && i>0) {
            calstr += "</div>";
        }
    }
    $("#results").append(calstr);
    // When a date-cell is clicked - changes color to green -> red -> white
    $(".calCell:not(.empty)").click(function() {
        changeColor($(this));
    });
};

JSFIDDLE

I also change the event to your Select Dropdown

It is more logical if it is .change() than .click()

$("#month, #year").change(function(e) {
   displayCalGrid($("#month").val(), $("#year").val());
});
rmondesilva
  • 1,732
  • 3
  • 17
  • 29
  • I didn't take into account the DOM change. Makes complete sense now that you say that. As for the `.change()` being more logical than `.click()`, I'm lost on the reason? From what I've researched, reasons have varied from use of keyboards to certain browsers, but I'm unsure if that applies to the logic with my code. Thanks for your help! – Gorgon_Union Apr 19 '16 at 03:29