2014-10-21 38 views
5

返回鏈式的承諾,這是取消 參見:http://jsbin.com/jeweke/2/

timer = $interval(intervalFunc, intervalDelay, 10); 
timer.then(
    function(res) {console.log('ok', res);}, 
    function(err) {console.log('err', err);} 
); 

但是,如果我鏈中的承諾,返回的承諾是不可取消。 請參閱:http://jsbin.com/jeweke/1/

timer = $interval(intervalFunc, intervalDelay, 10) 
.then(
    function(res) {console.log('ok', res);}, 
    function(err) {console.log('err', err);} 
); 

是怎麼回事?這是它應該如何工作?

注 - 這裏的例子是鬆散改編自http://jsfiddle.net/ExpertSystem/fZc3W/

回答

6

這是因爲從$interval承諾鏈的結果沒有包含間隔ID($$intervalId)的財產。第一種情況是您保存的計時器承諾中有$intervalId,第二種情況下您保存的是從原始q承諾返回的承諾,但不包含$intervalId屬性(這是在承諾上添加的定製屬性,用於存儲各自的setInterval當您致電​​時,您的身份證號碼)。當你取消定時器時,它需要$intervalId取消間隔並拒絕相應的定時器許諾。

這是interval.cancel

interval.cancel = function(promise) { 
     if (promise && promise.$$intervalId in intervals) { 
     intervals[promise.$$intervalId].reject('canceled'); 
     clearInterval(promise.$$intervalId); 
     delete intervals[promise.$$intervalId]; 
     return true; 
     } 
     return false; 
    }; 

注行: -

if (promise && promise.$$intervalId in intervals) { 

intervals不過是地圖intervalId及其各自承諾的(例如: - {1:promiseOfInterval1, 2:promiseOfInterval2}),所以沒有intervalId沒有取消發生。所以簡而言之,$ interval返回的promise是q promise和$ intervalId屬性,當你徹底鏈接時,它只是$q實現,它返回一個新的延遲對象的promise。

+0

很好的解釋。感謝您挖掘源代碼。 – RoyM 2014-10-21 22:52:39

+0

@roymath不客氣...... :) – PSL 2014-10-21 22:53:32