views:

52

answers:

4

Hello all.

I am going insane trying to figure out why this is not working. I am creating a checkbox dynamically with JS to enable/disable a text field (also created dynamically).

Code is pretty simple:

var text = $(document.createElement("input"));
text.type = "text";
container.appendChild(text);

...

var check = $(document.createElement("input"));
check.type = "checkbox";
check.onclick = function(event) {
    if (this.checked) text.enable();
    else text.disable();
};
container.appendChild(check);

I've tried putting the event handler after container.appendChild(check);, but that yields the same result.

There are no JS errors, and results are the same in Chrome, FF3.6, and IE7.

Can anyone explain why this isn't working? Any fixes would be appreciated.

Strangely (because theoretically it should be the same as above), adding the following (after container.appendChild(check);) works (checkbox is first on page):

$$("input[type=checkbox]")[0].onclick = function(event) {
    if (this.checked) text.enable();
    else text.disable();
};

I don't really like this, as it seems "dirty", and the checkbox may not be the first on the page later on...

BTW, $ and $$ are from Prototype.

Thanks in advance for any help.

A: 

Are you sure you don't have any errors?

craeteElement is misspelled in the first line. After fixing that, it all works on my machine with 1.6.1 and 1.7RC1.

http://jsfiddle.net/4XWP3/

Anurag
Sorry, that was my fault (typing error). It's spelled correctly in my code, and doesn't work...
Valera
does the link I posted work for you? if not, can you post a reproducible example of it on http://jsfiddle.net or somewhere else
Anurag
Yeah, the link works. But strangely, my code still doesn't work.
Valera
what version of Prototype? If the versions match too (1.6.1.0 or 1.7RC1), then something else in your code is breaking it.
Anurag
I'm using 1.6.1.0 right now. I'll try to look for something else that could be causing a conflict...
Valera
A: 

Works for me. Prototype is doing nothing for you here, so I'd suggest dropping it. The following works and simplifies things:

var text = document.createElement("input");
text.type = "text";
container.appendChild(text);

...

var check = document.createElement("input");
check.type = "checkbox";
check.onclick = function(event) {
    text.disabled = !this.checked;
};
container.appendChild(check);
Tim Down
Using $(...) wrappers for IE, to have Prototype methods tacked onto the new objects.
Valera
I've rewritten my answer.
Tim Down
The problem isn't that the handler doesn't work, it's that the handler doesn't even get fired. I can put an alert("") in there and click the checkbox and nothing happens.That's probably more efficient that what I had, so I'll probably use that...
Valera
The handler fires for me when I use `document.body` as the container, so there must be some other issue. Perhaps you could give more context?
Tim Down
container is really a div that's also dynamically created (and added to document.body). But I tried that on jsFiddle and it worked too. There's really not much more context than that.
Valera
A: 

Do you need to use the $(...) wrappers? Why not:

var text = document.createElement("input");
text.type = "text";
container.appendChild(text);
...
var check = document.createElement("input");
check.type = "checkbox";
check.onclick = function(event) {
    if (check.checked) text.enable();
    else text.disable();
};
container.appendChild(check);

Also, note that I changed if (this.checked) to if (check.checked) since this can get crazy in JS.

palswim
No need to change `this` to `check`: in this instance, `this` is guaranteed to be a reference to the checkbox. It's more useful to understand fully the rules about `this` than to avoid it entirely.
Tim Down
Using $(...) wrappers for IE, to have Prototype methods tacked onto the new objects.Tried both this. and check. but same results. I prefer using check. anyway, had it as this. from pasting out of HTML attribute...
Valera
+1  A: 

I figured out what was causing the problem...

After all of this code, I was adding some text by appending to innerHTML of container. For some reason, this threw off all of the event handlers for that container.

Using container.appendChild(document.createTextNode("...")); fixed the problem.

Hope this helps anyone else who might be having this sort of problem...

Valera
Aha! More context was needed :)
Tim Down
Yeah, I didn't realize that appending directly to innerHTML could interfere with it... Thanks for the help!
Valera