C#からWebBrowserコントロールを使ってみる


さて今日はプログラミングな話です。C#でIEコントロールをいじくってみます。

詳細はまだ明かせないのですが、現在C#で簡単なチャットプログラムを作成しておりまして、会話のログ表示部分にIEコンポーネント(WebBrowserコントロール)を使ってみようということにしました。私の確認する限りでは米国版のYahooメッセンジャーもこの方式が使われていて、会話ログの中にYouTubeの動画を埋め込むことができたりと、かなり強力です。

そこで今日はチャットプログラムでIEコンポーネントを効率よく使う方法についていろいろと自習をしていました。

今日わかったこと。

標準のダサいコンテクストメニューを切る方法。

チャットプログラムに「ソースを表示」とか「前に戻る」などの余計なメニューは要りませんので、自前でコンテクストメニューを実装してやる必要があります。

標準のコンテクストメニューを切るにはIsWebBrowserContextMenuEnabledプロパティをfalseにするだけで簡単に実現できるのですが、その代わりに独自に「コピー」や「すべて選択」などを入れたコンテクストメニューを自分で作ってやり、ContextMenuStripプロパティに設定してやる必要があります。こうすることで右クリック時にIE標準のコンテクストメニューの代わりに自分で作ったコンテクストメニューが表示されるようになります。

独自のコンテクストメニューで「コピー」や「すべて選択」の動作を実現するには?

さて、独自のコンテクストメニューを実装すると基本的にメニューアイテムが選択された場合の処理はすべて自分で実装しなければなりません。当然右クリックでコピーを行う動作等は独自に実装しないといけなくなります。

選択範囲のコピーを行うのはそれほど難しい事ではなく、
WebBrowser.Document.ExecCommand(“Copy”, false, null);
みたいな感じでコマンドを送ってやれば簡単に実現できます。

また、「すべて選択」を行うには”SelectAll”コマンドを同様に送ってやります。

要はこれらの動作を行うメソッドを作って、メニューアイテムのイベントハンドラに設定してやれば良いのです。

メニューアイテムの調整を行う必要がある。

しかしこのままでは、何の文字列も選択されていない状況でも「コピー」のメニューアイテムが有効になってしまうため、文字列が選択されていない状況ではなんらかの方法でこのメニューアイテムを無効にする必要があます。

幸いなことに、WebBrowser.Documentプロパティの中にContextMenuShowingというイベントがあり、このイベントを使う事で右クリックが行われてコンテクストメニューが表示される直前にイベントハンドラを呼ぶことができるので、ここにメニューアイテムのEnabled/Disabledの調整ルーチンを入れてやります。
ここでは「何らかのテキストが選択されていればコピーが選択可能」、「何のテキストも選択されていなければコピーが選択不可能」という機能を付けてみましょう。
WebBrowserコントロール上のテキストが選択されているかいないかを判別するのは、ちょっとやっかいで、標準のDocumentプロパティだけではできません。代わりにmshtml.IHTMLDocument2なるものを使う必要があります。この時「Microsoft.mshtml」を参照に追加するのを忘れないでください。
さて実際に、選択範囲のテキストを取得するには

mshtml.IHTMLDocument2 doc = (mshtml.IHTMLDocument2)this.webBrowser1.Document.DomDocument;

で、DomDocumentオブジェクトを取得してから、

mshtml.IHTMLTxtRange range = (mshtml.IHTMLTxtRange)doc.selection.createRange();
string selection = range.text;

とすることでselectionに選択部分の文字列が入ります。何も選択されていない場合にはnullになるので注意してください。とりあえずこれがnullかどうかを見てメニューアイテムの調整を行うと良いでしょう。

最終的に出来たもの

ie_customcontextmenu.png

標準のコンテクストメニューの代わりに独自に実装したコンテクストメニューが表示され、無事に機能しました。あとはこれをどんどん発展させていくだけです。

「C#からWebBrowserコントロールを使ってみる」への2件のフィードバック

コメントは停止中です。