Ruby on Rails | Screencasts | Download | Documentation | Weblog | Community | Source

Ticket #11007 (closed defect: duplicate)

Opened 2 years ago

Last modified 1 year ago

"style is null or not an object" error in IE7 caused by attempt to access style collection of document object

Reported by: jon.wind Assigned to: sam
Priority: normal Milestone: 2.x
Component: Prototype Version: edge
Severity: normal Keywords: 1.6.0.3
Cc:

Description

The "style is null or not an object" error in IE7 looks to be caused by an attempt to access the non-existent style collection of document object like so:

var value = element.style[style];

Changing a line in the getOffsetParent function seems to correct this by preventing getStyle from being called against the document object.

Old line:

while ((element = element.parentNode) && element != document.body)

Changed line:

while ((element = element.parentNode) && element != document.body && element != document)

Change History

02/05/08 04:02:09 changed by Tobie

  • cc set to kangax.
  • keywords set to 1.6.0.3.

02/05/08 04:43:12 changed by kangax

Well,

Element.getOffsetParent(document); // => <body>
Element.getOffsetParent(window); // => <body>
Element.getOffsetParent(5); // => <body>

I'm not sure if we should "fix" such edge cases. On the other hand, <body> being offsetParent of a document makes no sense whatsoever. Moreover (in FF):

document.body.offsetParent; // => null
document.offsetParent; // => undefined
window.offsetParent; // => undefined
new Element('div').offsetParent; // => null

I would vote for returning null in cases when offsetParent returns null, undefined, or throws an exception (IE6/7).

Thoughts?

02/06/08 07:02:27 changed by jon.wind

I probably wasn't clear enough in my initial post. The JS line that actually throws the "style is null or not an object" error is

var value = element.style[style];

in the Element.Methods.getStyle function when it's passed the document as the element by the getOffsetParent function. I'm not sure entirely sure why getOffsetParent is passing it the document as I haven't completely traced back through the call stack. I now see this error in IE7 when using an Ajax.Autocompleter that was working properly with Prototype 1.5.x.

Adding a test for the style attribute in getStyle (or wrapping it in a try, etc.) would be another resolution, and may result in a more bullet-proof getStyle, but preventing the call to getStyle in the getOffsetParent seemed to be an quick and dirty fix for my current problem.

02/06/08 17:02:01 changed by kangax

It's a little more complicated than that : ) Out of 63 methods that prototype extends elements with 38 fail when passed a document.

var i = 0;
for (var method in Element.Methods) {
  if (/Simulated|ByTag/.test(method)) continue;
  try { Element[method](document) }
  catch (e) { console.log(e, ++i) }
}

document is not an HTMLElement - it's a completely different interface - HTMLDocument http://www.w3.org/TR/DOM-Level-2-HTML/html.html#ID-26809268 We could of course run an explicit check in every one of those methods:

if (!Object.isElement(element)) return null;
// or
if (!Object.isElement(element)) throw new TypeError('Passed object is not an element');

The question is - does it really make sense to go after such edge cases and overkill essential methods?

02/11/08 22:19:09 changed by agrath

Just wanted to add that I was having the same error with my autocompleters as they fade in since my most recent upgrade and the suggested change to getOffsetParent definitely fixes the issue.

02/15/08 17:01:15 changed by elIkso

sorry for my english -- it's not my native language

i getting this bug with simplest calls, such as element#clonePosition

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>Untitled Document</title>

<style>
#div1 {
	width: 200px;
	height: 150px;
	background: red;
}
#div2 {
	position: absolute;
	width: 200px;
	height: 150px;
	background: yellow;
}
</style>

<script type="text/javascript" src="!js/prototype.js"></script>
<script type="text/javascript">
	function test () {
		$("div2").clonePosition($("div1"), { setWidth: false, setHeight: false, offsetLeft: 5, offsetTop: 25 });
	}
</script>

</head>

<body>

<a href="javascript://" onclick="test();">click me!</a>

<div id="div1">123</div>
<div id="div2">234</div>

</body>
</html>

changing getOffsetParent as jon.wind recommends fixes this issue

while ((element = element.parentNode) && element != document.body && element != document)

02/20/08 11:04:01 changed by vdelau

I'm also experiencing this problem with the scriptaculous autocompleter.

I'm patching my prototype.js with a slightly different method, although i'm not absolutely shure is it is better or worse:

while ((element = element.parentNode) && element != document.body && Object.isElement(element))

It should be a more generic check, but don't know if that is required. It works for me anyway :)

02/25/08 16:28:33 changed by jaquemet

Hi,

Just to add my stone to the pile, we were also having exactly the same issue since we PrototypeJS 1.6.0.2 and Scriptaculous 1.8.1 : Some autocompleters that were working fine ceased to work.

The problem was fixed by using modification on getOffsetParent() suggested above (used the one suggested by vdelau).

Olivier

(follow-up: ↓ 10 ) 03/27/08 19:09:30 changed by jdalton

  • status changed from new to closed.
  • resolution set to duplicate.

this issue resolved with this ticket + patch: http://dev.rubyonrails.org/attachment/ticket/11432

(in reply to: ↑ 9 ) 04/12/08 16:07:13 changed by elIkso

  • status changed from closed to reopened.
  • resolution deleted.

Replying to jdalton:

this issue resolved with this ticket + patch: http://dev.rubyonrails.org/attachment/ticket/11432

no, it's not true

.clonePosition() still triggering this error even with your modifications

(follow-up: ↓ 12 ) 04/12/08 16:24:56 changed by jdalton

  • cc deleted.
  • status changed from reopened to closed.
  • resolution set to duplicate.

Oops I posted the wrong patch link, try:
http://dev.rubyonrails.org/ticket/11473

Reopen ticket if that fails and please provide a sample code that demonstrates the failure.

(in reply to: ↑ 11 ) 04/12/08 16:38:44 changed by elIkso

Replying to jdalton:

Oops I posted the wrong patch link, try:
http://dev.rubyonrails.org/ticket/11473 Reopen ticket if that fails and please provide a sample code that demonstrates the failure.

now it works well

thx

10/10/08 22:06:10 changed by enguyen

By the way, I've put up a test page that shows how this bug will throw errors when using Position.clone():

http://jsbin.com/ulebe/

Use http://jsbin.com/ulebe/edit to modify the code, yourself. The two divs are superimposed in FF, but IE throws the error "'style' is null or not an object."