• 締切済み
  • すぐに回答を!

クリップボードからの貼り付けのフック

VB.net、C#、.net framework2005で、 クリップボード拡張ソフトを開発しております。 クリップボードへの入出力が起こる直前にフックをかけたいです。 コピー・切り取り操作(ClipBoardへの入力)については クリップボードチェーンに自分を加え、WM_DRAWCLIPBOARDをハンドルすることで解決できました。 貼り付け(ClipBoardからの出力)についてはどのようにすれば実現できますでしょうか? 貼り付けイベントが起こった時に、チェーン内のプログラムにそれを通知するようなWindowsメッセージがあるかと思い、それらしいものを探してみたのですが、利用できそうなものがありませんでした… 具体的には、 ・入力時に、データを加工して仮想クリップボードに格納 ・出力時に、仮想クリップボード内のデータを再度加工して出力(貼り付け) という処理を実現したいです。 宜しくお願い致します。

共感・応援の気持ちを伝えよう!

  • 回答数1
  • 閲覧数2448
  • ありがとう数2

みんなの回答

  • 回答No.1

 こんばんは。回答が付かないようですので。  外部の誰かがクリップボードを変更した瞬間に受け取りたいと言う事でしょうか。  クリップボードビューワに自分のウィンドウが登録されていれば、WM_DRAWCLIPBOARDで変更通知を受け取れる筈です。  http://jo0ls-dotnet-stuff.blogspot.com/2008/12/setclipboardviewer-api-vbnet.html  以下はクリップボードへビットマップが入る度にメッセージを出します。  PrintScreenキーを押してスクリーンショットを取れば直に確認出来ます。 Public Class Form1 Declare Unicode Function SetClipboardViewer Lib "user32.dll" (ByVal hWnd As IntPtr) As IntPtr Declare Unicode Function ChangeClipboardChain Lib "user32.dll" (ByVal hWnd As IntPtr, ByVal hWndNext As IntPtr) As Int32 Declare Unicode Function OpenClipboard Lib "user32.dll" (ByVal hWnd As IntPtr) As Int32 Declare Unicode Function CloseClipboard Lib "user32.dll" () As Int32 Declare Unicode Function GetClipboardData Lib "user32.dll" (ByVal uiFormat As UInt32) As IntPtr Const WM_CHANGECBCHAIN = &H30D Const WM_DRAWCLIPBOARD = &H308 Const CF_BITMAP = &H2 Private hWndNext As IntPtr Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load '自分をクリップボードビューワーに登録 Me.hWndNext = SetClipboardViewer(Me.Handle) End Sub Private Sub Form1_FormClosed(ByVal sender As System.Object, ByVal e As System.Windows.Forms.FormClosedEventArgs) Handles MyBase.FormClosed '自分をクリップボードビューワーから解除 ChangeClipboardChain(Me.Handle, Me.hWndNext) End Sub Protected Overrides Sub WndProc(ByRef m As Message) Select Case m.Msg Case WM_DRAWCLIPBOARD 'クリップボードの中を開いてビットマップだったらメッセージを出す OpenClipboard(Me.Handle) Dim hClipboard As IntPtr = GetClipboardData(CF_BITMAP) CloseClipboard() If hClipboard <> IntPtr.Zero Then MsgBox("クリップボードにビットマップが来ました") End If m.HWnd = Me.hWndNext Case WM_CHANGECBCHAIN If Me.hWndNext = m.WParam.ToInt32() Then Me.hWndNext = m.LParam.ToInt32() ElseIf Me.hWndNext <> IntPtr.Zero Then m.HWnd = Me.hWndNext End If End Select MyBase.WndProc(m) End Sub End Class

共感・感謝の気持ちを伝えよう!

質問者からの補足

御回答ありがとうございます。 質問の仕方が悪かったかもしれません。 それは上で言うクリップボードへの入力の際の話(クリップボードへの変更通知)ですよね?それに関しては仰るとおりWM_DRAWCLIPBOARDをハンドルすることで解決しております。 やりたいことは、システム全体での貼り付け行為(Ctrl+V)を監視して、その直前に処理を差し込むことです。具体的には、クリップボードのデータをその都度の任意のものに差し替えたいと思います。 キー(Ctrl+V)のグローバルフックでも出来ないことは無いのですが、キーの押しっぱなし等で連続して貼り付けが起こった場合、クリップボードのデータの同期タイミングにズレが生じます。 つまり、例えば貼り付けの度に連番(1,2,3...)を出力するような処理を差し込むとして、  1.Ctrl+V検知  2.クリップボードデータをn+1に差し替え(その後n++)  3.CallNextHookExで処理を流す  4.システムが貼り付け操作を実行 このフローにおいて、システムが4の操作を完了する前に新たなキーフックを検知してしまうと、貼り付け前にデータ差し替えが起こってしまい、実際の出力が1,2,4,5...等と歯抜けになってしまう問題に直面しています。 標題の質問に限らず、この問題を解決する何か良い方法をご存知の方、ご教示下さい。 宜しくお願い致します。

関連するQ&A

  • VC++2008 で クリップボードの監視を行いたい

    いつもおせわになっております。 ただいま、Visual C++ 2008 Express Edition を使いまして、クリップボード拡張アプリを作っております。 実装したい機能として・・・  A.クリップボードにデータがコピーされる度に、クリップボードのデータを取得する。  B.ただし、クリップボード上のデータは消さない。 というものがあります。 この使用を実装するために、下記のようにデータ存在の有無をタイマーな どでポーリングすれば良いと考えました。 >IDataObject ^data = System::Windows::Forms::Clipboard::GetDataObject(); >pictureShowPicture->Image->Dispose(); >if(data->GetDataPresent(DataFormats::Bitmap) == true){ しかし、この方法だと、一回でもデータがクリップボードにコピーされると、その後もずっと「データが存在する」状態となってしまい、新しいデータが来たのかどうか判断が出来ません。 クリップボード上のデータを消せば、「データが存在しない」状態となり、次にデータがコピーされたことが分かるのですが、クリップボード上のデータは消さない実装としたいのです。 このため、下記のようにすれば問題が解決できると思いました。  1.何らかの方法でクリップボードにデータがコピーされたという通知を受け取る。  2.現在のデータが直前のデータと同じか異なるかを判断する。    (ポーリングしておいて、データが異なれば新規データと判断) 上記1,2について、実現方法をご存知の方は教えていただけませんでしょうか。 ちなみに、受け取りたいデータ形式は、ビットマップ形式画像およびテキスト形式です。 お忙しいところ恐縮ですが、よろしくお願いいたします。

  • VB.NETでクリップボードの内容の転送

    VB.NETにて下記のプログラムを作成したいのですがどのようにすればよいのでしょうか? (1).市販のソフトの、入力項目(テキストボックス)にフォーカスを置く (2).VB.NETのプログラムで、入力項目に入れる内容をクリップボードに保存し、ボタンを押すと   (1)の入力項目(テキストボックス)に値が貼り付く パスワードを管理するフリーソフトで上記機能を実現しているので技術的には可能のようで、 いろいろ調べましたが解りませんでした。 (自分で作成したDelphiやPowerBuilderのプログラムでも出来ました) 以上、よろしくお願いします。

  • C#(VB.Net)でPhotoshopデータを扱いたい

    C#またはVB .NETで、Photoshop形式の画像データを扱いたいのですが、これを実現するdllやフリーソフトなどありますでしょうか。 C#またはVB.NETで構築する自作プログラムで、Photoshop形式のファイルを開いたり保存したりしたいのです。 Photoshop形式の画像加工までできればなおよいです。 .NETフレームワークのBitmapクラスのような手軽な方法で扱えるなら、なおよいです。 どなたかよい方法をご存知でしょうか。 ご回答お待ちしております。よろしくお願いします。

  • 音声入出力プログラムの作成方法を教えて下さい。

    音声チャットをするプログラムを作りたいと考えました。 言語は、Java, C++/C, C#, VB.NETであればなんでもいいです。 できれば、GUI部分が作りやすいC#, VB.NETであるといいですが。 特には限定しません。 私個人の状況の説明ですが、通信系のプログラムは、なんどか組んだことがあります。 ただし、通信の基になる情報の入出力源としては、 a)キーボード入力 b)DBの入出力 c)画面の入力内容を入力源とする。 d)通信結果で、画面を更新する。 e)コンソール入出力 f)ログ出力 主にテキストベースのやりとり。 通信時の構成としては、 AとBが通信するケースでは、 1)A→B方向での通信をするソケットを処理するスレッド 2)B→A方向での通信をするソケットを処理するスレッド B側にも同様に2つのスレッドがある状態。 セッションの確立要求を出すほうがクライアント側のソケットであるだけです。 受信部のロジックとしては、 a)改行コードがくるまでブロック。 受け取った情報を元に、アプリケーションプロトコルの処理し、再度ループを回る。 b)1バイト受信ごとに、処理をするループを回る。 (画面上の即時更新など) の2つ。 でも、音声だと、「マイク入力」、「スピーカーを鳴らす」、 そういう部分を解決しなければできないと思います。 DirectSoundや、SIPなどがあるようですが、正直難しくて手が出せてません。 スレッドやソケットは別にしても、テキストベースなら、コンソール入出力のように とても簡単なんです。 それに近いイメージでのノウハウで、アドバイスやサンプル等があるととても助かります。 言語は「Java, C++/C, VB.NET」であればよいです。動作環境は、OSはWindows一般でうごけばいいです。

  • StringGridの内容をクリップボードにCOPYしたい

    Borland C++ Builder 5 を使っています。 StringGridの内容をクリップボードにCOPYするプログラムを作っています。 Excelに貼り付けるのが目的なので、Tab区切りのデータにしています。 下に示したソースで実現できましたが、非常に遅いのです。 100行とか200行ならアッという間なのですが、2,000行、3,000行となるとかなり待たされます。 時間を食っているのは(2)の部分のようです。 もう少しスマートに、短時間でCOPYしたいのですが、方法はないものでしょうか? ◆ソースの解説 StringGridの21列分を、行数だけクリップボードにCOPYします。 (1) StringGridの各行、各列をLOOPしてセルに格納されている文字列長の合計を求めます。 Tab区切りにするため、各セルごと1バイト加算します。 また、各行ごと改行を入れるため、これも1バイト加算します。 (2) 合計容量が計算できたら、メモリーを動的確保し、もう一度LOOPをしながら、文字列をCOPYします。 セルごとにTab、行ごとに改行も追加します。 (3) 最後にクリップボードをクリアしてCOPYします。 int cnt = StringGrid1->RowCount; int size = 0; //StringGridのサイズ(文字長)をカウントする ------ (1) for(i=0;i<cnt;i++){ for(k=0;k<21;k++){ size += strlen(StringGrid1->Cells[k][i].c_str()) + 1; } size++; } //メモリーを確保して、StringGridをCOPYする -------- (2) cb = new char[size]; strcpy(cb,""); for(i=0;i<cnt;i++){ for(k=0;k<21;k++){ strcat(cb,StringGrid1->Cells[k][i].c_str()); strcat(cb,"\t"); //Tab区切りの文字列にする } strcat(cb,"\n"); } Clipboard()->Clear(); // -------- (3) Clipboard()->AsText = cb; なお、サイズがintに収まるかというチェックとか、メモリーの解放をする、といったことも必要ですが、記述を省略しました。

  • ツールボタンの制御について

    メールソフトやテキストエディタなどで編集系ボタン(切り取り 貼り付け、コピー、元に戻すなど)のツールボタンがある時 クリップボードとかにデータがなければ貼り付けが使用 できない(Enabled = false)とかになっていたりしますが これはどこのイベントで制御しているのでしょうか? DelphiだとTActionList(だったかな?)のようにメニューの イベントと連動して出来たのですが、C#ではどうすれば 良いのでしょうか? 現状は無理やりタイマーコントロールでクリップボードとか テキストボックスの選択文字数を監視してツールボタンの 有効/無効を切り替えています。

  • Javaでの画面コピーの取得方法

    Javaで画面コピーを取得する方法が分かりません。 ロボットで画面コピーをクリップボードにコピーして、クリップボードから画像を取得する方法は実現できました。 Robot robot = new Robot(); robot.keyPress(KeyEvent.VK_PRINTSCREEN); robot.keyRelease(KeyEvent.VK_PRINTSCREEN); BufferedImage image = (BufferedImage)clipboard.getContents(null);//画像データ クリップボードを経由しないで画面コピーを取得する方法はありますか?

    • ベストアンサー
    • Java
  • MAX10のINOUTの使い方

    MAX10のIOで、INOUTピンに設定し、データの入出力をしたいのですが、入出力時の切替は何か必要ですか。ポート記述でINOUTの設定をしています。記述は A <= INOUT (入力) INOUT <= A(出力) で良いのでしょうか。

  • ICのピンには入力・出力専用がある?

    (1)電源ピン、 (2)アドレスピン (3)データピン (4)制御ピン ↑この4つピンの中には (1)入力専用 (2)出力専用 (3)入出力専用 のピンがあると聞きましたが本当なんでしょうか? その際、この4つあるピンのうち、どれが入力専用・出力専用で、どのピンが入出力両方専用なのでしょうか? よろしくお願いいたします。

  • CSV出力に関する考え方

    先日よりPHPでのデータ加工方法を質問していますが、 CSV出力に関してどう考えたらいいのかがわかりません。 というのは、CSV出力したい場合に、 1.データをSQLで取り出したものを出力 2.データをSQLで取り出し、PHPで加工(画面イメージと同じようなもの)を出力 のどちらなのかについてです。 後者を行うための方法があればいいのですが、 前者だと1SQLでやりたい事を実現しなければならないのかと思い悩んでいます。 初心者な質問で申し訳ありませんがコメントお願いします。

    • ベストアンサー
    • PHP