.NET 2.0 axWebBrowserで表示しているページにJavascriptを挿入する | .NET Framework 2.0 と C#での開発ブログ

.NET 2.0 axWebBrowserで表示しているページにJavascriptを挿入する

以前に.NET 2.0 WebBrowserで表示しているページにJavascriptを挿入する方法を取り上げましたが、今回は私がaxWebbrowserでの開発に切り替えたこともあり、.NET 2.0 axWebBrowserで表示しているページにJavascriptを挿入する私なりの方法をご紹介します。


はじめに、どうもVS2005でのaxWebbrowserはAxSHDocVw, SHDocVwのバージョンが違うらしく(当たり前か)ググって見ても、情報はあるのですが、そのまま使えるって情報は今はあまりなかったです。
ああ、それと、当然mshtml.dllは使わない方法でのご紹介です。配布を考えたらmshtml.dllのサイズはありえないですからね。

まずはじめに、サンプルソースです。(あんまり参考にしないようにW)

------------------------------------------------
// ↓ <wbr>は意味無いけどなんかないとinsert出来ないので適当に入れてる。問題あるかも
string jsstr = "<wbr>\n";
jsstr = jsstr + "<SCRIPT DEFER language='JavaScript' type='text/JavaScript'>\n";
jsstr = jsstr + "<!-- \n";
jsstr = jsstr + " [ ここにJSを記述する ] \n";
jsstr = jsstr + "// -->\n";
jsstr = jsstr + "</SCRIPT>\n";

Type typ = Type.GetTypeFromCLSID(new System.Guid("{3050F4E7-98B5-11CF-BB82-00AA00BDCE0B}"));
object html_body = typ.InvokeMember("body", BindingFlags.GetProperty, null, axWebBrowser1.Document, null);

object[] args;
args = new object[] { "AfterBegin", jsstr };
typ.InvokeMember("insertAdjacentHTML", BindingFlags.InvokeMethod, null, html_body, args);
------------------------------------------------
(こうやってまとめると少ないな、、、時間かかったのに、、、)

さて、簡単に解説ですが、まず初めにScriptタグと実スクリプトをStringで作ります。
ここでの注意は見た人は必ず???ってなる <wbr> これですが、、、私も良くわかってないのですが、SCRIPTタグの前にスペースでもなんでもいいのでなにかがないと[insertAdjacentHTML]が私の場合出来なかったのです。これの理由はさっぱりで、これに気がつかなかったため、どんなに[insertAdjacentHTML]しても追加されないで長い間悩まされました。
たとえば、"<SCRIPT></SCRIPT>"を追加しても、実際にはなにも追加されません。次に"<div></div>"これはちゃんと追加されます。あと普通に"テスト"も問題なく追加されます。では、"<div><SCRIPT></SCRIPT></div>"とやるとどうなるでしょう?なんと "<div></div>" だけが追加されます。
 ふぬー意味わからんが[insertAdjacentHTML]はなんかやってるみたいですね。なので、色々実験した結果、たとえば"<br><SCRIPT></SCRIPT>"ってやるとちゃんとSCRIPTの部分も追加されることを発見しました。ってことは閉じるタグ無しのタグだったらいいのか、、、なんか抜け道っぽいっすね。
ただ、"<BR>"だと改行されてしまいますし、Headに入れるのも問題ですので、閉じるタグがいらない意味の無いタグを探して<wbr>にして見ました。<WBR>はNetscape Navigatorが独自に追加したタグで、<NOBR> - </NOBR>で自動改行をさせないようにした箇所の中で、改行しても良い位置を指定するために使われるそうです。まずめったなことでは使われないタグですね。IE系ではちゃんと無視されてるぽいですし、<NOBR>の中に無い限り無意味なのでこれにしました。これを<body>の直ぐあとにいれれば<NOBR>の中に入る可能性0ですね。
本来ならinsertAdjacentElementとかあればこんなことしなくてもいいのですが、これが見つからないんですねぇ~絶対あると思うのに。

つぎにmshtml.dllを使わない body の取得ですが、これはググれば情報あるので、完結に。
ようはaxWebBrowserのDocumentに対しInvokeMemberでbodyのプロパティを取得するってことっすね。

object html_body = typ.InvokeMember("body", BindingFlags.GetProperty, null, axWebBrowser1.Document, null);

↓objectの入れ物に
object html_body =

↓InvokeMemberを使って
typ.InvokeMember

↓bodyの要素を指定して
("body"

↓プロパティを取得
, BindingFlags.GetProperty

↓とりあえず無視
, null

↓axWebBrowserのDocumentから
, axWebBrowser1.Document

↓引数は無しよ
, null);

こんな感じ?

んでもって今度はInvokeMemberを使って[insertAdjacentHTML](追加)します。
今回は引数が必要なメソッドなのでまず、引数を指定します。
上記のサンプルでは 場所は"AfterBegin"で入れるのはjsstr(最初に作成したSCRIPTタグ)ですよ。って感じに。
んで、実際の処理ですが

typ.InvokeMember("insertAdjacentHTML", BindingFlags.InvokeMethod, null, html_body, args);

↓InvokeMemberを使って
typ.InvokeMember

↓利用したい名前を指定して
("insertAdjacentHTML",

↓メソッドを実行して
BindingFlags.InvokeMethod

↓とりあえず無視して
, null

↓bodyエレメントに対して
, html_body

↓この引数でお願いね
, args);

以上、これでちゃんと動きました。
以前のとちがって外部JSじゃなくていいので安心だし、無駄なファイルがなくていいですね。