[AS][JS]FLASHで「このページのトップに戻る」ボタンの設定
FLASHでブラウザのスクロールバーを最上部に戻す方法で、最初出来たと思いきや不完全だったのでメモ。
基本設定は以下の通り。
ステージサイズを500×1000くらいにしておく
インスタンス名:_mcのムービークリップをステージの下の方に配置。
まず最初のイマイチアプローチから
以下フレームアクション
//AS:フレームアクション _mc.addEventListener(MouseEvent.CLICK , xClick); function xClick (e):void { var tf = new TextField(); addChild(tf); tf.text = "リロードしてないよ"; navigateToURL(new URLRequest("#","_self")); }
これだけで出来ました。
ジャンプ先を#にするとブラウザリロードせずにページの先頭にジャンプできました。
先頭にはリロードしてないよの文字が表示されます。
で、これでいいや、と思いきや・・・
winのSafari3ではブラウザリロードしてしまいテキストが表示されません。
WINのIE6,7、FF3はリロードされなかったんですがね。。。
(HTMLの解釈的にはSafariの方が正しいっぽいような気がしますが)
というわけで別のアプローチ。
jsでスクロールバーを制御する方法。
js自体のソースはこちらのブログを参考にしました。
※イージングでゆっくりページのトップに戻るような処理のjsです。
//JS:HTMLに埋め込むか、jsファイルとしてhtmlで読み込むか function backToTop() { var x1 = x2 = x3 = 0; var y1 = y2 = y3 = 0; if (document.documentElement) { x1 = document.documentElement.scrollLeft || 0; y1 = document.documentElement.scrollTop || 0; } if (document.body) { x2 = document.body.scrollLeft || 0; y2 = document.body.scrollTop || 0; } x3 = window.scrollX || 0; y3 = window.scrollY || 0; var x = Math.max(x1, Math.max(x2, x3)); var y = Math.max(y1, Math.max(y2, y3)); window.scrollTo(Math.floor(x / 2), Math.floor(y / 2)); if (x > 0 || y > 0) { window.setTimeout("backToTop()", 25); } }
上記関数をhtmlに仕込んでおいて、Flash側には以下のように設定
//AS:フレームアクション _mc.addEventListener(MouseEvent.CLICK , xClick); // 呼びたいJSの関数名 var callJasFunction:String = "backToTop"; // JavaScriptの実行 function xClick (e):void { var tf = new TextField(); addChild(tf); tf.text = "リロードしてないよ"; ExternalInterface.call(callJasFunction) }
これでOKなのですが、Htmlにjs仕込むのが面倒くさい。
できることならFLASHだけで完結できないか、と。
と思ったら、こんな書き方でもFLASH上でJSを実行できるらしい。
//AS:フレームアクション _mc.addEventListener(MouseEvent.CLICK , xClick); // 呼びたいJSの関数 var callJasFunction:String = "function backToTop() {var x1 = x2 = x3 = 0;var y1 = y2 = y3 = 0;if (document.documentElement) {x1 = document.documentElement.scrollLeft || 0;y1 = document.documentElement.scrollTop || 0;}if (document.body) {x2 = document.body.scrollLeft || 0;y2 = document.body.scrollTop || 0;}x3 = window.scrollX || 0;y3 = window.scrollY || 0;var x = Math.max(x1, Math.max(x2, x3));var y = Math.max(y1, Math.max(y2, y3));window.scrollTo(Math.floor(x / 2), Math.floor(y / 2));if (x > 0 || y > 0) {window.setTimeout('backToTop()', 25);}}"; // JavaScriptの実行 function xClick (e):void { var tf = new TextField(); addChild(tf); tf.text = "リロードしてないよ"; ExternalInterface.call(callJasFunction) }
ようは、関数名のところに関数全部書いちゃってもOKみたい。
これなら、Html変更しなくていいから楽チンだ!
と思いきや、これだと不具合ありました・・・
jsの再帰処理的な部分が実行されず、最初の一回しか実行されてないっぽい。
↓ここの部分
//上述したJSの一部を抜粋 if (x > 0 || y > 0) { window.setTimeout("backToTop()", 25); }
でも最初の一回は実行されるので、一回でトップに戻るようなjsなら問題なくページの頭だしは可能。
jsをこれだけにすれば、とりあえずイージングなしの頭だしは可能でした。
//AS:フレームアクション _mc.addEventListener(MouseEvent.CLICK , xClick); // 呼びたいJSの関数 var callJasFunction:String = "function backToTop() {window.scrollTo(0, 0);}"; // JavaScriptの実行 function xClick (e):void { var tf = new TextField(); addChild(tf); tf.text = "リロードしてないよ"; ExternalInterface.call(callJasFunction) }
※2009/5/12追記
以下の書き方で再帰処理も可能でした。
document.insertScriptなんてものを使えばよいのだね。
JSよくわかんね。
_mc.addEventListener(MouseEvent.CLICK , xClick); // 呼びたいJSの関数名 var callJasFunction:String = "document.insertScript = function(){ backToTop = function() {var x1 = x2 = x3 = 0;var y1 = y2 = y3 = 0;if (document.documentElement) {x1 = document.documentElement.scrollLeft || 0;y1 = document.documentElement.scrollTop || 0;}if (document.body) {x2 = document.body.scrollLeft || 0;y2 = document.body.scrollTop || 0;}x3 = window.scrollX || 0;y3 = window.scrollY || 0;var x = Math.max(x1, Math.max(x2, x3));var y = Math.max(y1, Math.max(y2, y3));window.scrollTo(Math.floor(x / 2), Math.floor(y / 2));if (x > 0 || y > 0) {window.setTimeout('backToTop()', 25);}}}"; var method = " backToTop"; //上記関数を読み込み(この段階では、関数backToTopは実行されないみたい) ExternalInterface.call(callJasFunction) // JavaScriptの実行 function xClick (e):void { //ここで初めて実行されるみたい。 ExternalInterface.call("backToTop") }
Tweet