3 Quick Steps for a Painless Upgrade to jQuery 1.3
read 20 commentsSince the release of jQuery 1.3 a month and a half ago, I've been keeping my eye on any troubles that people have had with their upgrades. Fortunately, most people have had no problems at all. For those who have, the issues have almost always been in one of three areas. Identifying these areas and adjusting any legacy scripts ahead of time will go a long way toward ensuring a smooth transition to jQuery 1.3.x.
1. Update Attribute Selectors
By far the most common stumbling block to the 1.3 upgrade has been the attribute selector. The XPath syntax for this selector — [@attribute] — has been deprecated since version 1.1.4 in August, 2007. Still, many scripts, including some prominent plugins, continued to use the old syntax, which wasn't a problem until jQuery 1.3, at which point it was no longer supported. The correct syntax (since 1.1.4) follows the CSS standard: [attribute].
The fix is quite simple. Simply search your scripts for [@. Go through the matches one by one, and if the string is being used as an attribute selector (and not, for example, in a regular expression), replace it with [.
Removed XPath Syntax
This will break your code in jQuery 1.3+:
- $('a[@href^=http]');
- $('[@title=foo]');
Current CSS Syntax
Use this instead:
- $('a[href^=http]');
- $('[title=foo]');
2. Check Custom Selectors
If you are using custom selectors, either in your own script or within a plugin, you might run across an error if the second argument's object value is a string:
- jQuery.extend(jQuery.expr[':'], {
- hasSiblings: "jQuery(a).siblings(m[3]).length>0"
- });
This is another easy fix. Simply change that value to an anonymous function and add what was in the string to the return statement:
- jQuery.extend(jQuery.expr[':'], {
- });
So, basically, you just change "jQuery(a).siblings(m[3]).length>0" to function(a,i,m) {return jQuery(a).siblings(m[3]).length>0;}.
When someone on the jQuery Google Group was having trouble with George Adamson's excellent More Selectors plugin, all I had to do to make it compatible with jQuery 1.3 was update the attribute selectors and change custom selectors (my updated script is available here temporarily until George has time to update the original).
3. Note Visible and Hidden Elements
This change didn't occur until jQuery 1.3.2, but if you are upgrading to the latest and greatest jQuery version, you'll want to be sure your scripts aren't relying on a quirk in how jQuery was determining the visibility of elements. Prior to 1.3.2, if you had an element with display:block inside a containing element with display: none, the inner element would still be reported as visible.
- <div id="outer1" style="display:none">
- <div id="inner1">
- you can't see me!
- </div>
- </div>
Before version 1.3.2, $('#inner'1).is(':visible') would return true and $('#inner1:hidden') would match 0 elements. In order to find out if an element were truly hidden, meaning you couldn't see it, you'd have to check all of its ancestors to see if they were hidden as well. Remy Sharp put together a little custom selector to check if elements were *really* visible.
With 1.3.2, $('#inner').is(':visible) returns false and $('#inner:hidden') match 1 element.
Another Visible Wrinkle
There is one more change in how visibility is detected in 1.3.2: elements with visibility: hidden are now considered visible, whereas before they were considered hidden.
- <div id="outer2">
- <div id="inner2" style="visibility: hidden">
- you can't see me!
- </div>
- </div>
Given the above div structure, jQuery 1.3.2 considers #inner2 visible while prior versions considered it hidden.
Here is a quick demo, with two iFrames showing the differences in determining visibility:
I'm not sure how I feel about the new behavior with visibility:hidden, but I think the change was important for performance reasons.
A Few Others
There are a few other issues that may affect a small minority of users, but the three above represent the lion's share of reported problems that I've seen on the Google Groups. For more information about changes, see the jQuery 1.3 Release Notes
















As Usual great job Karl
The first step affects the validation plugin. If you're using it, upgrade to 1.5.1!
'elements with visibility: hidden are now considered visible, whereas before they were considered hidden'
Really?? Care to explain the thinking behind that one?
I've been trying to figure out why my :visible selectors are broken in 1.3 for a while now, and ended up abandoning it altogether and using a specific class name.
Hi Steve,
I tracked down John Resig's explanation on the jQuery Dev Google Group:
visibility:hidden elements are still "on the page" taking up space, even though they are transparent. If it is a link element, for example, and you hover it, an underline will appear, even though the link is visibility:hidden.
So technically, some of their attributes are still "visible".
Good,thanks!!
Damn, I am pretty sure the ":visible" change broke the zebra striping functionality of the TableSorter plugin....
Starting to poke through the code now but it's a large uphill climb
I just tested a table sorter demo with 1.3.2 and zebra stripping is working. I'm using TS 2.0.3
I was upgrading a page that uses the Thick Box plug-in this weekend and it seems to be broken. The selected image would not come to the screen. Reverting back to an older jQuery fixed the problem.
Hi William,
Can you provide a link to the version of thickbox that you're using? If so, I'd be happy to help track down the problem or contact Cody Lindley about it. Cheers.
Karl:
I saved a copy of Thick Box website as a MHT file when I first gained interest in the plug-in. It is ThickBox 3.1 and the file is dated 1/21/2008. Does that help?
If you need more information let me know.
WBR
On line 79 of http://jquery.com/demo/thickbox/thickbox-code/thickbox.js, change this:
TB_TempArray = $("a[@rel="+imageGroup+"]").get();to this:
TB_TempArray = $("a[rel="+imageGroup+"]").get();Great info, Karl. Thanks!
Sadly, most of my pain will be updating incompatible plugins.
I'm concerned about the visibility thing. Consider this case:
<div class="pane">
<div class="pane-header">
<div class="closeable">
<a href="#">[-]</a>
</div>
</div>
<div class="pane-content">
stuff here that can be slid up
</div>
</div>
So, this describes a title bar with a close box. The code may not be perfect, cuz it's air code, but you get the idea. Then the jQuery (which also is air code and could be written more concisely):
$(".pane-header > .closeable").click(function() {
var pane = this.parents('.pane');
var content = pane.find('.pane-content');
if(content.is(':visible')) {
pane.find('.closeable a').text('[-]');
content.slideUp(300);
}
else {
pane.find('.closeable a').text('[+]');
content.slideDown(300);
}
});
The question is: When I slideUp the content, will content.is(':visible') then be false, as expected or is there some other result?
Hello,please add you site at http://www.sweebs.com among other best sites available on the net!
Regards
Kris
Thanks for posting this Karl, I have picked up alot from it, but still having a few problems with updating a great plugin by Karel Jan http://sandbox.tinctuur.be/tree/ just wondering if you could point me in the right direction with it?
Hi Adrian,
It looks like that plugin is using jQuery UI as well. If you update jQuery to 1.3.x, you'll need to update to jQuery UI 1.7.x, too.
If you're still having problems after you've updated everything, let me know. Or, post the question on the jquery-ui Google Group.
I try upgrade to jQuery 1.3.2 and UI 1.7.2, but sortable Tree doesn´t work. (http://sandbox.tinctuur.be/tree/ )
Is there any solution to fix it?
Soon to be launched WordPress 2.8 will come bundled with jQuery 1.3.2. Up from 1.2.6.
While updating my plugin, I hit a few errors. The first resource I turn to for solutions is this page.
Thanks a lot Karl.
Thanks for summarizing them here ...