鍍金池/ 教程/ Android/ jQuery 3 中的新變動(dòng)
101 種讓你的網(wǎng)頁(yè)看起來(lái)更酷的方法
Android 項(xiàng)目是如何使用 Kotlin 語(yǔ)言生成的 1/2
Nimbledroid 版本更新
使用TypeScript提高開發(fā)能力
利用 TensorFlow Serving 系統(tǒng)在生產(chǎn)環(huán)境中運(yùn)行模型
Google Play 榜單APP冷啟動(dòng)速度分析報(bào)告
使用微信控制電腦(Python 版)
jQuery 3 中的新變動(dòng)
RxAndroid 基礎(chǔ):第一部分
Swift in 2016
UI自動(dòng)化測(cè)試基于Activity的封裝模式
2016年,有哪些適合你學(xué)習(xí)的編程語(yǔ)言?
Swift 響應(yīng)式編程
如何組合使用 VIM 編輯器與 IPYthon
如何使你的app更加流暢
介紹用來(lái)選擇輪廓圖像的一個(gè)類——Will J Miller
關(guān)于Android N 開發(fā)者預(yù)覽版的一些隨想

jQuery 3 中的新變動(dòng)

http://wiki.jikexueyuan.com/project/geekdigest/images/jquery-3-header.jpg" alt="" />

譯者:李鑫

原文:What’s New in jQuery 3

本文為極客學(xué)院Wiki組織翻譯,轉(zhuǎn)載請(qǐng)注明出處。

時(shí)間:2016.3.11

十年前 jQuery 的出現(xiàn)震撼了整個(gè) Web 開發(fā),如今它的一些優(yōu)秀特點(diǎn)仍非常適用。利用 jQuery,用戶可以方便地與 DOM 進(jìn)行交互,執(zhí)行 Ajax 請(qǐng)求,創(chuàng)建動(dòng)畫,等等。另外,與 DOM API 不同的是,jQuery 實(shí)現(xiàn)了復(fù)合模式(composite pattern)。正因?yàn)檫@一特點(diǎn),你可以在一個(gè) jQuery 集合中調(diào)用一些 jQuery 方法,而不用擔(dān)心集合包含的元素?cái)?shù)量(沒(méi)有、只有一個(gè)或很多)。

隨著 jQuery 3 的發(fā)布,jQuery 會(huì)到達(dá)一個(gè)重要的里程碑。該版本修復(fù)了很多 Bug,添加了一些新方法,不建議采用或干脆清除了一批函數(shù),并改變了一些函數(shù)的行為。本文將重點(diǎn)介紹 jQuery 3 所帶來(lái)的一些關(guān)鍵改動(dòng)。

1 新特性

下面就將逐條介紹 jQuery 所新增的一些關(guān)鍵特性。

1.1 for...of 循環(huán)

jQuery 3 現(xiàn)在允許利用 for... Of 來(lái)遍歷 jQuery 集合的 DOM 元素。這種新的迭代器是 ECMAScript 2015(也就是 ECMAScript 6)規(guī)范的一部分。它能實(shí)現(xiàn)對(duì)可遍歷對(duì)象(包括 Array、Map、Set 等)的循環(huán)。

在使用這一新迭代器時(shí),接收的值并不是每次訪問(wèn)一個(gè)元素的 jQuery 集合,而是一個(gè) DOM 元素。這一迭代器稍微改變了對(duì) jQuery 集合執(zhí)行操作的方式。

下面舉例來(lái)介紹這種迭代器的工作原理。假設(shè)頁(yè)面上的每一 input 元素都需要指定一個(gè) ID。jQuery 3 之前的做法是:

var $inputs = $('input');

for(var i = 0; i < $inputs.length; i++) {
   $inputs[i].id = 'input-' + i;
}

到了 jQuery 3,你只需這樣寫:

var $inputs = $('input');
var i = 0; 

for(var input of $inputs) {
   input.id = 'input-' + i++;
}

1.2 $.GET()$.POST() 的新簽名

jQuery 3 為 $.get()$.post() 這兩個(gè)工具函數(shù)添加了新的簽名,為的是跟 $.ajax() 對(duì)等。新的簽名是這樣的:

$.get([settings])

$.post([settings])

settings 是一種能夠執(zhí)行很多屬性的對(duì)象,和提供給 $.ajax() 的對(duì)象相同。關(guān)于詳細(xì)介紹,請(qǐng)參考 $.ajax() 頁(yè)面的內(nèi)容。

跟傳遞對(duì)象給 $.ajax() 相比,當(dāng)傳遞對(duì)象給 $.get()$.post() 時(shí),其唯一區(qū)別在于 method 屬性一直被忽略。原因在于 $.get()$.post() 各有一種預(yù)設(shè)的 HTTP 方法來(lái)處理 Ajax 請(qǐng)求($.get()GET$.post()POST)。一般說(shuō)來(lái),不能用 $.get() 發(fā)送 POST 請(qǐng)求。

考慮下面這段代碼:

$.get({
   url: 'https://www.audero.it',
   method: 'POST' // 該屬性被忽略   
});

盡管有 method 屬性,該語(yǔ)句還是不能發(fā)送 POST 請(qǐng)求,只能發(fā)送 GET 請(qǐng)求。

1.3 動(dòng)畫可以使用 REQUESTANIMATIONFRAME()

所有現(xiàn)代的瀏覽器,包括 Internet Explorer 10 及更高版本,都支持 requestAnimationFrame。而在這背后,jQuery 3 將在執(zhí)行動(dòng)畫時(shí)使用該 API,從而實(shí)現(xiàn)動(dòng)畫更平滑,減少 CPU 的工作壓力。

1.4 UNWRAP()

jQuery 3 為 unwrap() 添加了可選的選擇器參數(shù)。這一方法的新簽名為:

unwrap([selector])

有了這一變動(dòng),就能將一個(gè)包含選擇器表達(dá)式的字符串傳入父元素進(jìn)行匹配查找。如果存在匹配,那么與之匹配的子元素將解包,否則操作無(wú)法完成。

2 已更改的特性

下面是 jQuery 3 已經(jīng)調(diào)整了的一些特性行為。

2.1 :VISIBLE:HIDDEN

新版 jQuery 更改了 :visible:hidden 過(guò)濾器的含義。如果元素有布局框,包括那些寬度和/或高度為0的情況,則元素被認(rèn)為是:visible。比如說(shuō),br 元素和沒(méi)有內(nèi)容的內(nèi)聯(lián)元素將可以通過(guò) :visible 過(guò)濾器進(jìn)行選擇。

所以,假如頁(yè)面有如下標(biāo)記:

<div></div>
<br />

如果運(yùn)行了下面語(yǔ)句:

console.log($('body :visible').length);

那么在 jQuery 1.x 和 2.x 時(shí),結(jié)果是 0,而到了 jQuery 3,結(jié)果就是 2。

2.2 DATA()

另一改動(dòng)就是跟 data() 方法的行為有關(guān)。調(diào)整主要是為了讓該方法符合 Dataset API 規(guī)范。jQuery 3 將所有屬性的鍵都改為駝峰式大小寫形式。先看下面這個(gè)例子。

<div id="container"></div>

如果使用 3 之前的版本寫了下列代碼:

var $elem = $('#container');

$elem.data({
   'my-property': 'hello'
});

console.log($elem.data());

控制臺(tái)上的結(jié)果如下:

{my-property: "hello"}

而在 jQuery 3,結(jié)果為:

{myProperty: "hello"}

所以再次重申:jQuery 3 時(shí),屬性名都是駝峰大小寫,沒(méi)有中間的短劃線(-);而使用 3 之前的版本,則依然采用全部小寫字母的寫法,詞之間帶有短劃線。

2.3 Deferred 對(duì)象

jQuery 3 還改變了 Deferred 對(duì)象的行為(該對(duì)象是 Promise 對(duì)象的前身),改善了它與 Promise/A+ 提案的兼容性。該對(duì)象及其歷史非常有意思,你可以讀讀官方文檔,也可以看看我寫的書 《jQuery 實(shí)戰(zhàn),第 3 版》中有關(guān) jQuery 3 的章節(jié)內(nèi)容。

在 jQuery 1.x 和 2.x 時(shí),傳入 Deferred 中的回調(diào)函數(shù)中的一個(gè)未捕獲異常會(huì)導(dǎo)致程序停止執(zhí)行。與原生的 Promise 對(duì)象不同的是,拋出異常會(huì)逐層傳播,直到它抵達(dá) window.onerror 為止(往往是這樣)。如果不能為該事件(雖然并不常見)定義一個(gè)函數(shù),則會(huì)顯示異常消息,程序終止執(zhí)行。

jQuery 3 遵循原生的 Promise 對(duì)象的模式。因此,拋出的異常將被視為一個(gè) rejection,從而執(zhí)行失敗回調(diào)。完成之后,進(jìn)程繼續(xù),繼續(xù)執(zhí)行后續(xù)的成功回調(diào)。

為了讓你理解這其中的差異,先來(lái)看一個(gè)小例子。如下所示:

var deferred = $.Deferred();

deferred
  .then(function() {
    throw new Error('An error');
  })
  .then(
    function() {
      console.log('Success 1');
    },
    function() {
      console.log('Failure 1');
    }
  )
  .then(
    function() {
      console.log('Success 2');
    },
    function() {
      console.log('Failure 2');
    }
  );

deferred.resolve();

在 jQuery 1 和 jQuery 2 時(shí),只執(zhí)行第一個(gè)函數(shù)(拋出錯(cuò)誤的函數(shù))。另外,因?yàn)闆](méi)有為 window.onerror 定義處理器,所以控制臺(tái)將輸出消息:“Uncaught Error: An error”(未捕獲的錯(cuò)誤:發(fā)生錯(cuò)誤),程序不再繼續(xù)執(zhí)行。

而在 jQuery 3,行為則完全不同了,控制臺(tái)將顯示 “Failure 1” 和 “Success 2” 兩個(gè)消息。由第一個(gè)失敗的函數(shù)來(lái)管理異常,一旦被處理,則繼續(xù)執(zhí)行下面的成功函數(shù)。

2.4 SVG 文檔

jQuery 各個(gè)版本(包括 3)都沒(méi)有對(duì) SVG 文檔有過(guò)官方的支持。但實(shí)際上很多方法都適用,另外一些方法,比如操作類名的方法,已經(jīng)在 jQuery 3 中進(jìn)行了更新,因此也適用。因此,在未來(lái)的版本中,應(yīng)該可以使用 addClass()hasClass() 這樣的方法處理 SVG 文檔,估計(jì)不會(huì)出現(xiàn)什么問(wèn)題。

3 過(guò)時(shí)不建議采用與已清除的方法及屬性

除了前面說(shuō)的改進(jìn),jQuery 3 還除去了一些方法和屬性,并且聲明了一批不建議采用的特性。

3.1 不建議采用:BIND()、UNBIND()、DELEGATE()UNDELEGATE()

不久前引入的 on() 方法代替了 jQuery 的 bind()、delegate() 以及 live() 方法,提供了一種統(tǒng)一的訪問(wèn)接口。與之類似,jQuery 用 off() 方法來(lái)代替 unbind()、undelegated()die() 方法。bind()、delegate()、unbind()undelegate() 今后不建議使用,也不會(huì)再支持它們。

jQuery 3 將所有這些方法聲明為過(guò)時(shí),并打算在未來(lái)版本中清除它們(有可能是 jQuery 4),所以今后一定要在項(xiàng)目中堅(jiān)持使用 on()off() 方法,以便適應(yīng)將來(lái)的變化。

3.2 已清除的方法:LOAD()UNLOAD()ERROR()

jQuery 3 完全棄用了已被宣布為過(guò)時(shí)的方法:load()、unload()error()。這些方法已經(jīng)過(guò)時(shí)很長(zhǎng)時(shí)間了(從 jQuery 1.8 起),但仍一直存在著。如果某個(gè)插件依賴其中的一個(gè)或多個(gè)方法,那么更新到 jQuery 3 時(shí),代碼就會(huì)出錯(cuò),因此一定要在更新時(shí)多注意一下這個(gè)問(wèn)題。

3.3 已清除的屬性:CONTEXT、SUPPORTSELECTOR

jQuery 3 清除了 context、supportselector 屬性。如前所述,如果項(xiàng)目中仍然使用著這些屬性,或者某個(gè)插件仍在依賴這些屬性,那么更新到 jQuery 3 時(shí),代碼就會(huì)出錯(cuò)。

4 修復(fù)的 Bug

jQuery 3 修復(fù)了前一版本的一些重大 Bug。下面介紹兩個(gè),此次修復(fù)將會(huì)對(duì)你的編碼產(chǎn)生重大影響。

4.1 width()height()

此次修復(fù)了 width()height() 以及其他連帶方法中的 Bug。這些方法再也不會(huì)四舍五入到最近的像素了,因?yàn)樵谀承┣闆r下,這樣做很難定位元素。

舉例來(lái)說(shuō)明這一問(wèn)題。假設(shè)寬度為 100 px 的 container 元素包含著 3 個(gè)子元素。

<div class="container">
   <div>My name</div>
   <div>is</div>
   <div>Aurelio De Rosa</div>
</div>

在 jQuery 3 之前的版本,獲取子元素寬度的代碼應(yīng)該是下面這樣吧?

$('.container div').width();

這樣一來(lái),結(jié)果就是 33。因?yàn)楫?dāng)時(shí) jQuery 會(huì)將結(jié)果 33.33333 四舍五入。而在 jQuery 3 中,這個(gè) Bug 已經(jīng)得到修復(fù),你的結(jié)果會(huì)更精確(比如會(huì)得到浮點(diǎn)數(shù))。

4.2 WRAPALL()

jQuery 3 還修復(fù)了一個(gè)將某個(gè)函數(shù)傳入 wrapAll() 方法時(shí)常會(huì)出現(xiàn)的 Bug。在 3 之前的版本中,當(dāng)把某個(gè)函數(shù)傳入 wrapAll() 時(shí),會(huì)將 jQuery 集合中的元素分別包裝。換句話說(shuō),它的行為表現(xiàn)得就像將函數(shù)傳入 wrap()。

除了修復(fù)這個(gè)問(wèn)題外,因?yàn)檫@種函數(shù)在 jQuery 3 中只會(huì)被調(diào)用一次,所以jQuery 集合元素的索引不可能被傳入。最后,該函數(shù)上下文(this)將指向 jQuery 集合中的第一個(gè)元素。

5 下載 jQuery 3 beta 1

如果此文讓你產(chǎn)生了興趣,你可以試試 jQuery 3 的第一個(gè) beta 版。通過(guò)下面兩個(gè) URL 都可以下載到它。

利用 npm 也可以下載它,命令如下:

npm install jquery@3.0.0-beta1

6 總結(jié)

許多人宣稱 jQuery 已死,認(rèn)為現(xiàn)代 Web 開發(fā)已經(jīng)不需要它了。但 jQuery 的開發(fā)仍在繼續(xù),而且統(tǒng)計(jì)數(shù)字顯示,前100萬(wàn)個(gè)網(wǎng)站中,采用這一技術(shù)的網(wǎng)站占到了 78.5%,從而駁斥了上述反對(duì)言論。

本文只是列出了 jQuery 3 所帶來(lái)的一些主要改變。你可能會(huì)注意到,這一版本更新不會(huì)對(duì)已有項(xiàng)目產(chǎn)生太大的影響,因?yàn)闆](méi)有引入太多破壞性的徹底變革。盡管如此,仍然需要注意一些因素,比如 Deferred 對(duì)象的改進(jìn)。就像更新第三方依賴所經(jīng)常要面的那樣,對(duì)項(xiàng)目一定要做一個(gè)復(fù)查,從而防止意外行為或功能崩潰的情況出現(xiàn)。