人気ブログランキング | 話題のタグを見る
Studio TA Subsite の案内とお知らせ

CSSで作るマスク:スクロールトラップ防止(1)

2016年 10月 17日
スクロールトラップという言い方は勝手に作った言葉ですが、ブラウザ画面をスクロールをしている最中に、マウスポインターがページ内の縦スクロールのあるブロック(スクロールボックス)にさしかかった場合、スクロールがそのブロックに移ってしまう事を言ってます。

マウスポインターをスクロールを捕られたブロックから移動させれば、全体画面のスクロールを再開できますが、少々うっとうしいものです。「スクロールの中断を回避でき、しかもユーザーが選択すれば、そのブロックのスクロールも出来る様にする」というのは、案外と難しい注文です。

考え方としては、問題のブロックの上に透明マスクを配置し、それをクリックした時はマスクが消滅して下のブロックのスクロール操作やリンクを押せる様にします。 クリックしない時は、スクロール操作でマウスポインターがブロック上を通過しても、実際は透明マスク上を通過しているので、スクロールがトラップされる事が無いという塩梅です。 マスクはクリックで消滅しますが、これをCSSで実現する場合、この復活は使うコードで変わって来ると思われます。 具体的には「:checked」を使うか「:focus」を使うか等で変わるという話です。

今回は試作段階ですが「:focus」を使ってテストしています。 この透明マスクは、スクロールトラップ防止という目的で作っていますが、誤操作防止やそのコメントを表示する事、あるいはもっと他の用途にも使えるかも知れません。



最初にコードを示します。 以下のコードをtextファイルにし、適当な名前で「.html」の拡張子で保存すれば、ブラウザ上で実際の動きを確かめる事が出来ます。(リンク文字列のリンク先はフェイクですから、押すとありませんの表示になります)


<html>
<head>
<title>コードテスト</title>
<style>

.alink {
margin: 0px 10px 0px; }

input.sw {
width: 120px;
padding: 0;
border-width: 0;
opacity: 0.5;
transition-delay: 0.4s;
height: 40px;
margin: 0px 0px -30px; }

input.sw:focus {
height: 0px;
margin: 0px 0px 10px; }

</style>
</head>
<body>
<br>
<br>

<div>
<input type="button" class="sw" />
<div><a class="alink" href="other.html">リンク文字列</a></div>
</div>

<br>
<br>
</body>
</html>



この動き方をハードコピーで示します。

最初にブラウザで開くと、下の様に「リンク文字列」の上にくすんだマスクが覆って表示されます。 このマスクは、実際に使うコードでは「opacity: 0;」に設定して完全な透明にしますが、ここでは動作が判る様に「opacity: 0.5;」と半透明にしています。

CSSで作るマスク:スクロールトラップ防止(1)_b0174191_23465794.png

下の様にポインターを「リンク文字列」上に持って行っても、実際はマスク上に持って行った事になり、ポインターの形は変わりません。 下のこの段階では、マスク下の「リンク文字列」には触ることが出来ません。(下にあるのがスクロールボックスならスクロール出来ないという事です)

CSSで作るマスク:スクロールトラップ防止(1)_b0174191_23470191.png

一度この場所(マスクの上)でクリックすると、マスクが「height: 0;」となり「リンク文字列」が表に出ます。(マスクが透明なら、ユーザーは最初のクリックでリンクが押せず2度目で押せると思うだけです) 「リンク文字列」が表に出たので、下の様にポインターが手の形に変わります。

CSSで作るマスク:スクロールトラップ防止(1)_b0174191_23470705.png

リンクを押すと本来はリンク先に飛びますが、このテストコードの「リンク文字列」は実際には無いリンク先を書いてあるので、ブラウザは表示できないと答えます。

下はリンクを押さず、一旦ポインターを「リンク文字列」の上から退けたところです。

CSSで作るマスク:スクロールトラップ防止(1)_b0174191_23471323.png

このコードは「:focus」を使っています。 最初にマスクをクリックした時にマスクに focusが移っています。 ブラウザ画面内の他の要素をクリックするまで、この focusは続きます。 スクロールボックスのスクロールや要素のフォバーでは focusの状態は変化しません。 そして、上の状態では画面上のどこをクリックしても、マスク以外の場所に focusが移り、下の様にマスクが元の状態に戻ります。

CSSで作るマスク:スクロールトラップ防止(1)_b0174191_23471786.png

以上がこのマスクの動作です。

ただし、ちょっと工夫が必要な事があります。 マスクの下のリンクを押す事でも focusが移動するので、結果としてマスクが戻ってリンクが押せないのです。 これでは困るので「transition-delay: 0.4s;」という遅延動作を設定しています。 このプロパティは、動作が始まるまでのタイミングを0.4secと指定するもので、focusが移ってマスクされるのを少し遅らせて「リンク文字列」を押してしまえというわけです。 妙なコードですが、実際に「0.1s」等の設定では押せず、「0.4s」位だとだいたい押せる様です。 もっと遅いとより確実ですが、今度はマスクが開くのが遅くなります。

このマスクがスクロールトラップ防止にちゃんと使えるかテストしてみました。「リンク文字列」の代わりに簡単なスクロールボックスを作り、マスクもそのサイズに合わせて試してみました。

CSSで作るマスク:スクロールトラップ防止(1)_b0174191_08322184.png

上はクリックする前で、マスクされて全体のスクロールが邪魔されません。 下はクリック後で、ボックスにアクセス出来、スクロールバーの操作やリンクのクリックが問題なく出来ました。

CSSで作るマスク:スクロールトラップ防止(1)_b0174191_08355444.png

目的の通りに使えそうです。



このブログの右メニュー「以前の記事」に実装したマスクは、このコードを応用しています。
これはスクリプト等を使用せずに、CSSで実現できる特殊なマスクのアイデアです。

一般に、CSSで状態の変化を切り替える動作を実現するコードは、「input」の「checkbox」を使うものが良く紹介されています。 しかし、上に紹介したのは「input」の「button」を利用していますが、このコードは以下の特徴があります。

●「button」自身にサイズを持たせてマスクにしているので、labelを使わないでシンプルなコードになっています。
●ラベルを使用する場合は「id」を使う事になりがちですが、このコードでは不要です。 これは「id」を重複できないルールから逃れる事が可能で、実はエキサイトのメニューに利用する場合に必要な条件なのです。

「button」の代わりに「checkbox」を使った方法は次のページに載せます。



by Ataron | 2016-10-17 01:03 | ブログスキンのアレンジ | Trackback | Comments(0)
名前
URL
削除用パスワード

※このブログはコメント承認制を適用しています。ブログの持ち主が承認するまでコメントは表示されません。