FirefoxとOperaで問題なく動作するGreasemonkeyスクリプトがあります。ただし、Chromeで動作させるのに苦労しています。問題は、ページからコードによって呼び出すことができる関数をページに挿入することです。これが私がこれまでに行っていることです:
まず、 FirefoxのunsafeWindowへのヘルパーリファレンスを取得します。これにより、FFとOpera(およびChrome)で同じコードを使用できるようになります。
var uw = (this.unsafeWindow) ? this.unsafeWindow : window;
次に、ページに関数を挿入します。これは実際には非常に薄いラッパーであり、GMスクリプトのコンテキストで対応する関数を呼び出すだけです。
uw.setConfigOption = function(newValue) {
setTimeout(setConfigOption, 0, newValue);
}
次に、私のスクリプトに対応する関数があります。
setConfigOption = function(newValue) {
// do something with it, e.g. store in localStorage
}
最後に、関数を呼び出すためのリンクを含むHTMLをページに挿入します。
var p = document.createElement('p');
p.innerHTML = '<a href="javascript:setConfigOption(1)">set config option to 1</a>';
document.getElementById('injection-point').appendChild(p);
要約すると、Firefoxでは、ユーザーがその挿入されたリンクをクリックすると、unsafeWindowで関数呼び出しが実行され、GMスクリプトのコンテキストで対応する関数を呼び出すタイムアウトがトリガーされ、実際の処理が実行されます。(ここで間違っている場合は訂正してください。)
Chromeでは、「Uncaught ReferenceError:setConfigOptionisnotdefined」エラーが発生します。実際、コンソールに「window.setConfigOption」と入力すると、「undefined」が生成されます。FirebugとOpera開発者コンソールには、機能があります。
これを行う別の方法があるかもしれませんが、私の関数のいくつかはページ上のFlashオブジェクトによって呼び出されるため、ページコンテキストに関数がある必要があると思います。
私はGreasemonkeywikiでunsafeWindowの代替案をざっと見てみましたが、それらはすべてかなり醜いように見えます。私はここで完全に間違った方向に進んでいますか、それともこれらをもっと詳しく調べる必要がありますか?
解決策:MaxSをフォローしました。アドバイスとそれは今FirefoxとChromeの両方で動作します。ページで使用できるようにする必要のある関数を通常の関数にコールバックする必要があったため、スクリプト全体をページに移動しました。つまり、彼が「main()」と呼んだ関数に完全にラップされています。
そのハックの余分な醜さをもう少し耐えられるようにするために、少なくともunsafeWindowとwrappedJSObjectの使用をやめることができます。
私はまだGreasemonkeywikiからコンテンツスコープランナーを機能させることができていません。同じように動作するはずで、正常に実行されているように見えますが<a>
、たとえば、ページの要素から関数にアクセスすることはできません。それがなぜなのか、私はまだ理解していません。