※この記事は8年以上前の記事です。
現在は状況が異なる可能性がありますのでご注意ください。
どうも、禁ゲーの禁断症状で死にそうなみやびです。
もうね、会社行かなくなる勢いだからねマジ。
さて、表記の件やっていこう。
これね、全部スクロール無効にすんなら簡単なんだよ。
例えば、下記HTMLの、div#testTargetをスワイプした時はスクロールさせない、とか。
●HTML
<body> <div id="testTarget" style="overflow-y: auto; height: 200px;"> <p> あかさたな はまやらわ <span style="display: block; margin-top: 800%;">わをーーーん</span> </p> </div> </body>
●JavaScript(jQuery)
$('#testTarget').on('touchmove.noScroll', function(e) { e.preventDefault(); });
ターゲットDOMに対して、このようにイベントを追加すればいい。
ただし、これやるとどうなるかってと、
div自体のスクロールも不能になる。
例えば、サイドバーを表示する時、
サイドバーの高さが高い時なんかは、コンテンツの下のほうが見えなくなる。
そしたらねぇ、自分でスクロールを作るしかない。
※jQuery使ってます。
$('#testTarget').on('touchmove.noScroll', function(e) { e.preventDefault(); });//div上では全部スクロールできないようにする。 //共通変数を定義 var scrollYStart = 0, scrollYMove = 0, swipeTime = new Date(); var scrollAction = function(setDom, d, spd){ setDom.stop().animate({scrollTop: d}, spd, 'easeOutQuint'); }; $(function(){ $('#testTarget').bind({ touchstart: function(e) { //タッチ始め $(this).stop();//アニメーションストップ scrollYStart = event.changedTouches[0].pageY;//タッチ始めの座標 scrollYMove = scrollYStart; swipeTime = new Date();//タッチ始めの時間 }, touchmove: function(e) { //スワイプ中 var posY = event.changedTouches[0].pageY,//スワイプ中の座標 scrollNow = $(this).scrollTop();//現在のスクロール var lastSc = scrollNow + scrollYMove - posY; scrollAction($(this), lastSc, 0.5);//スクロールを実行 scrollYMove = posY;//スワイプ中座標を格納 }, touchend: function(e) { //タッチが終わった時 var lastY = scrollYStart - scrollYMove;//どれだけスワイプしたか var nowT = new Date();//タッチ終了時間 var difTime = nowT.getTime() - swipeTime.getTime();//スワイプ経過時間 if (difTime < 601) { //601ミリ秒以内のスワイプなら実行 var scP = (lastY < 0 ? lastY * -1: lastY) / difTime * 100;//追加スクロール量計算 var lastScroll = $(this).scrollTop() + (lastY < 0 ? -1 * scP : scP);//スクロール位置 scrollAction($(this), lastScroll, 700); } } }); });
見ればわかると思うけど、
touchstart、touchmove、touchendの三点セットを使って、
スクロールを再現してるわけだ。
スタートでスワイプ開始時間をとり、タッチ終了時との時間比較で、
短ければ、スワイプとみなし、アニメーションで追加スクロールをする。
これを使えば、
サイドバーを表示している間は、bodyはスクロールさせないで、
その中身をスクロール、なんてできる。
設定数値を変えれば、スクロールの感じを変えることができる。
iPhoneでやればそれっぽくって設定したつもり。
やり方は全然違うが、下記エントリーが非常に参考になった。
●タッチイベントを用いたスワイプ&フリックの実装サンプル
これやるのに、えらく苦労したんだよ。
最初は、背景要素とコンテンツ要素を分け、背景要素にだけ、スクロール禁止をし、
対象要素だけ、デフォルトのスクロールをそのまま残すようにした。
だが、それだと、対象要素をスクロールしている間に、bodyが動いてしまう時があった(特にiPhone)
しかし、これなら、そんなんもクリアできる。
問題はデバイスのスペックだけど、
現代のデバイスならだいたいいけると思う。
さて、帰るかね・・・。
コメントする