WWW Watch

jQuery 3.0 および jQuery Compat 3.0 のアルファ版が公開される

jQuery 3.0 および jQuery Compat 3.0 のアルファ版がリリースされました。主に .show()、.hide() メソッドに対して行われた仕様変更について触れてみたいと思います。

jQuery米国時間の 13日付けで、jQuery 公式サイトにてアナウンスされましたが、jQuery 3.0 および jQuery Compat 3.0 のアルファ版がリリースされました。

現行版の jQuery 2.x 系の後継が 「jQuery 3.0」、1.x 系の後継が 「jQuery Compat 3.0」 と名称変更されてのリリースになります。大きいところだと .show().hide() メソッドの仕様が変わったみたい。

jQuery 3.0 and jQuery Compat 3.0 Alpha Versions Released

jQuery のバージョン番号については、過去に下記の記事で触れています。1.x 系、2.x 系で別れてしまっていたバージョン番号を統一し、わかりやすくするのが狙いです。

.show().hide() メソッドの仕様変更

.show().hide() メソッドの仕様変更については、公式 Blog 内でも説明されていますが、下記のように変更されるそうです。

So, instead, we're experimentally defying the evolution of these methods and reverting to a simple, primordial model. This will break some code. If you have elements in a stylesheet that are set to display: none, the .show() method will no longer override that. So the most important rule for moving to jQuery 3.0 is this: Don't use a stylesheet to set the default of display: none and then try to use .show() - or any method that shows elements, such as .slideDown() and .fadeIn() - to make it visible.

If you need an element to be hidden by default, the best way is to add a class name like "hidden" to the element and define that class to be display: none in a stylesheet. Then you can add or remove that class using jQuery's .addClass() and .removeClass() methods to control visibility. Alternately, you can have a .ready() handler call .hide() on the elements before they are displayed on the page. Or, if you really must retain the stylesheet default, you can use .css("display", "block") (or the appropriate display value) to override the stylesheet.

jQuery 3.0 and jQuery Compat 3.0 Alpha Versions Released : Official jQuery Blog から引用

要点だけを簡単に訳すと、

  • もし、ある要素に CSS で display: none; が指定されていた場合、.show() はその要素の display プロパティを上書きしない (要するに display: block; などとしてくれない)。
  • jQuery 3.0 で最も大きなルールの変更は 「CSS で display: none; した要素に .show() を使うな (同じ表示系のメソッドである .slideDown().fadeIn() も同様に)」 ということ。

という仕様変更が行われましたと。また、この変更に対する対策として、

  • 初期状態で display: none; した要素が必要なら、class 指定して CSS を当てよう。その上で、.addClass().removeClass() メソッドを使えば要素の表示 / 非表示を制御できる。
  • .ready() イベント内で .hide() を使用して非表示にした要素を、再度表示させる用途なら .show() は使える。
  • 要素に CSS で指定された display プロパティの状態を保持しながら表示を制御するなら、.css("display", "block") ("block" 部分は適切なものに変えることができる) を使用するのがよい。

要するに、1.x / 2.x 系までの仕様だと、CSS 側で display: none; された要素を .show() したとき、強制的に style="display: block;" (対象要素のデフォルト CSS による) を付与することで表示されるようにしてたわけです。

また、CSS 側で display: inline-block; などとした要素を .hide() してから、再度 .show() した場合などは、元々指定されている display: inline-block;style="display: inline-block;" という形で付与して、表示を元に戻すという面倒なことをやっていましたが、これらの処理はとても煩雑で、要素の数が多かったりするとパフォーマンス的にも不利になっていました。

それに加えて、最近はメディアクエリによって各要素の display 値が変わったりとか色々と面倒な事が多いので、もう style="display: ****;" という形で style 属性を付与するのはやめましたと。これが .show() に対する大きな変更ということになります。

具体的に同挙動が変わるかというと、例えば下記のような jQuery のコードがあったとして、

$(document).ready(function(){
  $(".sample-section").hide();
  $(".btn-show").click(function() {
    $(".sample-section").show();
  });
});

jQuery 3.0 でも 2.x 系まででも、.btn-show をクリックした時に .sample-section が表示されるという点で、動作的には同じように見えるんですが、表示に至までの課程が異なります。

2.x 系までは、クリック操作によって、.sample-section に対して style="display: block;".sample-section が div 要素だったと仮定すれば) が付与されることで、結果として要素が表示されます。

それに対して、3.0 では、.sample-section に対して .hide() メソッドが付与した style="display: none;" の style 属性値を空に ( style="" ) することで要素が表示される挙動になります。

ですから、jQuery 3.0 では、CSS 側で display: none; されていると、.show() ではそれを上書きできませんということになるわけですね。

既存の Web サイトに jQuery 3.0 を導入する際、旧来の動作を前提にコードが書かれていると問題が起こる可能性がありますので、注意が必要かと思います。

そもそも CSS 側で display: none; しておいて、.show() で表示っていう設計は JavaScript が無効だったり、万が一 jQuery の読み込みに時間がかかったりした際に、表示切り替えができなくなってアクセシビリティを損ねますので避けるべきですけどね。

ソースコードを修正する必要がない場合でも、3.0 系にすることで、.show().hide() メソッドのパフォーマンスは向上することになります。

その他、jQuery.Deferred が Promise/A+ と互換性を持って使用できるようになったり、1.6.x の時に一時導入されながら削除されてしまっていた requestAnimationFrame が復活していたりと、派手さはないですが色々と改善、新機能が取り入れられていますので、正式リリースが楽しみかもしれません。

関連エントリー

Recent Entry

全ての記事一覧を見る

Hot Entry

逆引きおすすめエントリー