My HTML looks something like this (unfortunately it cannot change because it is being rendered with the CMS I am using):
<li>
<input id="cb1" type="checkbox">
<label for="cb1">
<div>Some Other Content</div>
<div class="pledge">Click to Pledge</div>
</label>
</li>
The jQuery.
$("div.pledge").click(function() {
var checkboxlabel = $(this).parent("label");
$("input[for=checkboxlabel]").attr('checked', !$checkbox.attr('checked'));
});
Using this code will toggle the checkbox if I click anywhere inside the label. What I need is for the action to only take place when I click the <div class="pledge">
element. I suspect that .stopPropagation(); will help me here but I have not been able to get it to work properly.
Here is another shot that seems to be accomplishing the same think:
$("div.pledge").click(function() {
$("input[for=' + this.parent("label").attr("id") + ']").attr('checked', !$checkbox.attr('checked'));
});
Reading between the lines, it seems to me that the following will achieve your desired result without any JS:
<li>
<input id="cb1" type="checkbox">
<div>
<div>Some Other Content</div>
<label for="cb1">Click to Pledge</label>
</div>
</li>
http://jsfiddle.net/nnnnnn/VqmBb/
This displays "Some Other Content" and "Click to Pledge" next to the checkbox, but as you can see with my demo only the "Click to Pledge" part checks/unchecks the box when clicked.
I've swapped your label and the "pledge" div around, and made use of the label's for
attribute to associate it with the checkbox so that it will automatically check/uncheck it. (Though now the outer div doesn't actually do anything and could be removed unless you need it for styling.)
Regarding your JS, the following line has some problems:
$("input[for=checkboxlabel]").attr('checked', !$checkbox.attr('checked'));
First, your selector "input[for=checkboxlabel]"
seems to be trying to use the checkboxlabel
variable declared on the line before, but what you've actually done is just include a string that happens to include the text "checkboxlabel". So that won't select any elements in your html because you have no "input" element with a "for" attribute equal to the string "checkboxlabel". Also you've got a variable $checkbox
that isn't defined anywhere.
UPDATE: OK, the following should work for your updated html (it worked for me). The problem with your existing JS code, apart from the fact that you are trying to use a variable, $checkbox
, that isn't declared, is that you are trying to bind your click handler to the "pledge" div which means you haven't done anything to handle clicks on other parts of the label. Given that you specifically want to stop clicks on other parts of the label I'd suggest that you attach the .click()
handler to the label - clicks on the label's children will bubble up to the label's click handler, so then you can test whether the element that was clicked was the one with class "pledge". If not return false
to cancel the default behaviour for a label click, but if it is the "pledge" element do nothing and let the default happen:
$("div.pledge").parent("label").click(function(e) {
if (!$(e.target).hasClass("pledge"))
return false;
});
(Note I'm selecting the parent of "div.pledge" rather than just saying $("label").click()
so that this processing doesn't get attached to all labels.)
If you don't like that I think mgibsonbr's answer is a nice alternative.