之前專案中的列表是採用的iscroll
,但是在使用iscroll
有乙個問題就是:當內容不足全屏的時候,是木有辦法往下拉的,這樣就達不到重新整理的目的了。【這是本人工作中遇到的,具體例子具體分析,這裡只作乙個參考】
大致的例子是這樣的:
那麼,既然超過一屏是可以重新整理的,那我們就來逛逛**吧。在github上搜尋iscroll,開啟第乙個,找到src
下面的core.js
。
首先既然要下拉,肯定會觸發touchstart
、touchmove
以及touchend
事件。搜尋touchmove
,很好,在_initevents
中的註冊了這個事件。
_initevents: function (remove)
// ...
},
好吧,看到這裡的時候,我表示懵了一下逼,這不就是個繫結事件麼?this
又是乙個什麼鬼,然後我去查了一下文件,發現了這麼乙個東西。文件位址
target.addeventlistener(type, listener[, options]);
target.addeventlistener(type, listener[, usecapture]);
target.addeventlistener(type, listener[, usecapture, wantsuntrusted ]);
//
// gecko/mozilla only
listener
當所監聽的事件型別觸發時,會接收到乙個事件通知(實現了 event 介面的物件)物件。listener 必須是乙個實現了 eventlistener 介面的物件,或者是乙個函式
木有看錯,listener
是乙個物件或者是乙個函式。前提是這個物件實現了eventlistener
介面。我們接著往下看,發現了這麼乙個例子。
var something = function(element)
};// note that the listeners in this case are |this|, not this.handleevent
element.addeventlistener('click', this, false);
element.addeventlistener('dblclick', this, false);
// you can properly remove the listeners
element.removeeventlistener('click', this, false);
element.removeeventlistener('dblclick', this, false);
}var s = new something(document.body);
然後在去iscroll
的原始碼去找,發現了同樣的實現方式。在default
資料夾中有乙個handleevent.js
。
好了,這個梗先告一段落。還是繼續看原始碼。在handleevent.js
中,有這麼一段東西。
handleevent: function (e)
}};
發現在start/move/end
分別呼叫了內部方法_start/_move/_end
方法。去看看這三個方法,看其中可能會引起不會滑動的點。
在_start
方法中,看到這樣的幾行**,會不會是直接返回了呢?分析分析:
if ( !this.enabled || (this.initiated && utils.eventtype[e.type] !== this.initiated)
// ...
var point = e.touches ? e.touches[0] : e,
pos;
this.initiated = utils.eventtype[e.type];
this.moved = false;
initiated
屬性在最開始肯定是沒有的,而enabled
預設是true
,所以在最開始執行這個方法的時候是不會返回的,而是會給initiated
這個屬性設定當前的eventtype
值,這個值會在_move
方法中用到。重點來看看_move
方法。
if ( !this.enabled || utils.eventtype[e.type] !== this.initiated )
首先來進行型別判斷,因為在_start
方法中已經定義了這個值,所以這裡也不會返回。接著往下看:
if ( timestamp - this.endtime > 300 && (absdistx < 10 && absdisty < 10) )
【實際上是兩次click事件的模擬】如果兩次滑動的時間大於了300ms,並且只要乙個方向上的位移少於10畫素,那麼也是會返回的。那麼會不會呢,打個斷點測試一下就知道了。這裡就不貼圖了,實際中的測試結果是,每一次移動肯定是在300ms以內的,這裡之所以判斷300ms,主要是click
事件執行會有乙個300ms的延遲。而每一次移動,由於手指的觸點比較大,還是會大於10畫素的,即使兩次不大於10畫素,也是不影響的。所以這點不會返回。那麼繼續接著看:
// if you are scrolling in one direction lock the other
if ( !this.directionlocked && !this.options.freescroll ) else if ( absdisty >= absdistx + this.options.directionlockthreshold ) else
}if ( this.directionlocked == 'h' ) else if ( this.options.eventpassthrough == 'horizontal' )
deltay = 0;
} else if ( this.directionlocked == 'v' ) else if ( this.options.eventpassthrough == 'vertical' )
deltax = 0;
}
第乙個條件判斷只要是定義了這次滑動的方向是什麼。h
表示水平方向,v
表示豎直方向。我們是要向下滑動,所以我們關注的是豎直方向。看第二個條件判斷,如果是豎直方向,那麼將水平方向的deltax
值變為0。這樣做的目的是保持絕對的豎直方向。因為移動實際還是根據元素的位移值來的。當probe
的版本為2以下的時候,是根據css3的transform
屬性來移動位移的,為3版本的時候是根據決定對位來移動的。所以這裡只要不把我們的deltay
置為0就說明木有什麼問題。繼續往下看**:
deltax = this.hashorizontalscroll ? deltax : 0;
deltay = this.hasverticalscroll ? deltay : 0;
newx = this.x + deltax;
newy = this.y + deltay;
// ...
// 這裡是移動
this._translate(newx, newy);
測試中發現,這個hasverticalscroll
一直是false
,那麼deltay
一直就是0,也就是移動了也白移動。找到問題原因。那麼,這個hasverticalscroll
是從**來的?全域性找呀找,在refresh
中找到這樣幾行**:
var rect = utils.getrect(this.scroller);
/* replace start: refresh */
this.scrollerwidth = rect.width;
this.scrollerheight = rect.height;
/* replace end: refresh */
this.hashorizontalscroll = this.options.scrollx && this.maxscrollx < 0;
this.hasverticalscroll = this.options.scrolly && this.maxscrolly < 0;
針對以上問題,只要我們能夠使內部的滾動部分高度大於容器高度,那麼就能觸發滾動。
2.1 粗略做法
可以設定乙個min-height
屬性為900px
(900只是乙個示例,只要夠大就可以),這樣就可以保證可以滑動。
2.2 精準做法
計算當前的容器高度,然後比容器高度多乙個畫素即可。
IScroll的那些事 內容不足時下拉重新整理
之前專案中的列表是採用的iscroll,但是在使用iscroll有乙個問題就是 當內容不足全屏的時候,是木有辦法往下拉的,這樣就達不到重新整理的目的了。這是本人工作中遇到的,具體例子具體分析,這裡只作乙個參考 大致的例子是這樣的 那麼,既然超過一屏是可以重新整理的,那我們就來逛逛 吧。在github...
基於iScroll實現內容滾動效果
一 iscroll簡介 iscroll 是一款針對web app使用的滾動控制項,它可以程式設計客棧模擬原生ios應用裡的滾動列表操作,還可以實現縮放 拉動重新整理 精確捕捉元素 自定義滾動條等功能。這裡博主使用的版本iscroll4.25,目前最新版本是iscroll5,大家可以去官網 官網位址 ...
那些人,那些事
很久沒有整理一下自己的思緒,聽著熟悉的歌,那歌聲會讓我想起那些人,那些事.乙個標點,乙個符號,乙個個早已在歲月深處冰封的眼神,一段沒有伴侶的歸途。一直以來我都認為我的人生就是這樣,平平淡淡,安安靜靜,波瀾不驚地在歲月的 眼角劃過,不留絲毫痕跡。現在看來,原來我寫的東西在很大程度上是是在滿足自己的某種...