C# と VB.NET の質問掲示板

ASP.NET、C++/CLI、Java 何でもどうぞ

C# と VB.NET の入門サイト

SendMessageについて


(過去ログ 8 を表示中)

[トピック内 11 記事 (1 - 11 表示)]  << 0 >>

■8322 / inTopicNo.1)  SendMessageについて
  
□投稿者/ すー 二等兵(4回)-(2006/11/15(Wed) 21:29:26)

分類:[VB.NET] 


分類:[VB.NET] 

お世話になっております。
APIを使用してアプリ間のメッセージ、文字列のやり取りを以下の手順で考えています。

1.RegisterWindowMessageでユニークなメッセージを定義します。
2.アプリAでアプリBのウインドウハンドルを検出し、そのハンドルに対して、SendMessageを使用して定義したメッセージと文字列を送ります。
3.アプリBのWndProcをoverrideして送信されたメッセージを受信します。
4.文字列を解析してアプリBの処理を分岐します。

メッセージの受信は問題なくできるのですが、文字列をうまく受信することができません。
SendMessageのlParamに文字列を設定しているのですが、受信するとm.lParamに数値が入っています。
文字列を取得するにはどのようにいいのでしょうか?
お手数ですが教えてください。

0
引用返信 編集キー/
■8323 / inTopicNo.2)  Re[1]: SendMessageについて
□投稿者/ 渋木宏明(ひどり) 一等兵(36回)-(2006/11/15(Wed) 21:46:19)
渋木宏明(ひどり) さんの Web サイト

分類:[VB.NET] 

> SendMessageのlParamに文字列を設定しているのですが、受信するとm.lParamに数値が入っています。

異なるプロセス間で、lParam に文字列を詰めて送ることなんかできません。

WM_SETWINDOWTEXT 等、一部のメッセージについて、Windows が特殊処理を行っています。

wParam, lParam で表せる2つの整数値よりも多くの情報を送信したいなら、WM_COPYDATA を使用する他に道はありません。


0
引用返信 編集キー/
■8396 / inTopicNo.3)  Re[2]: SendMessageについて
□投稿者/ すー 二等兵(5回)-(2006/11/20(Mon) 09:15:03)

分類:[VB.NET] 

お世話になってます。

亀レス大変申し訳ありません。
lParamでは文字列はダメなんですね。パラメータなのでできるものだと思い込んでいました。

教えていただいた「WM_COPYDATA」を検索してみたのですが、VB.netのサンプルが見当たりませんでした。
VB6のサンプルを参考にして以下のように組んで見たのですが、メッセージ送信結果がエラー(0)となります。

'COPYDATASTRUCT構造体の設定する
Dim sdtCOPYDATASTRUCT As COPYDATASTRUCT
sdtCOPYDATASTRUCT.dwData = 0
sdtCOPYDATASTRUCT.cbData = 3
sdtCOPYDATASTRUCT.lpData = "ABC"

'送信先のハンドルを取得する
Dim hWndTo As Integer = FindWindow(vbNullString, "Form1")

'メッセージを送信する
SendMessage(hWndTo, WM_COPYDATA, Me.Handle.ToInt32, sdtCOPYDATASTRUCT)

どなたかアドバイスをお願いします。

0
引用返信 編集キー/
■8397 / inTopicNo.4)  Re[3]: SendMessageについて
□投稿者/ Blue 中尉(158回)-(2006/11/20(Mon) 09:26:30)

分類:[VB.NET] 

COPYDATASTRUCT構造体はどのように宣言していますか?

一応C#の場合は
http://dobon.net/cgi-bin/vbbbs/srch.cgi?no=0&word=WM_COPYDATA&andor=and&logs=all&PAGE=20&search_day=
な感じです。
(FreeHGlobalが抜けていますけど)


0
引用返信 編集キー/
■8402 / inTopicNo.5)  Re[4]: SendMessageについて
□投稿者/ Blue 大尉(160回)-(2006/11/20(Mon) 10:48:42)

分類:[VB.NET] 

2006/11/20(Mon) 15:57:12 編集(投稿者)

VB用に書き直してみた。

Imports System
Imports System.Runtime.InteropServices

Public Class CopyDataTest
Private Const WM_COPYDATA As Integer = &H4A
<DllImport("user32.dll")> _
Private Shared Function FindWindow(ByVal lpClassName As String, ByVal lpWindowName As String) As IntPtr
End Function
' ※ WM_COPYDATA用にlParamの型をByRef lParam As COPYDATASTRUCT にしてある。
' そのほかにSendMessageを多用するのであれば、IntPtrにするか(Marshal.StructureToPtrを使う)、
' 関数名を変えるなどして対処する。
<DllImport("user32.dll")> _
Private Shared Function SendMessage _
(ByVal hWnd As IntPtr, ByVal Msg As Integer, _
ByVal wParam As IntPtr, ByRef lParam As COPYDATASTRUCT) As IntPtr
End Function

Private Structure COPYDATASTRUCT
Public dwData As IntPtr
Public cbData As Integer
Public lpData As IntPtr
End Structure

Public Shared Sub Main(ByVal args() As String)
Dim hWnd As IntPtr
Dim cds As COPYDATASTRUCT
Dim s As String

hWnd = FindWindow(Nothing, "recv")

If Not hWnd.Equals(IntPtr.Zero) Then
s = "ほげ"

cds = New COPYDATASTRUCT
cds.dwData = IntPtr.Zero
cds.lpData = Marshal.StringToHGlobalUni(s)
cds.cbData = (s.Length + 1) * 2
SendMessage(hWnd, WM_COPYDATA, IntPtr.Zero, cds)

Marshal.FreeHGlobal(cds.lpData)
End If
End Sub
End Class


0
引用返信 編集キー/
■8411 / inTopicNo.6)  Re[5]: SendMessageについて
□投稿者/ すー 二等兵(6回)-(2006/11/20(Mon) 14:41:48)

分類:[VB.NET] 

お世話になってます。

Blue さま

サンプル大変ありがとうございます。
しかしながら、私のスキル不足で受け側がよくわかりません。C++のサンプルを見たのですが理解不能です。
もしよろしければ、受け側の方も教えていただけませんでしょうか?
お手数ですがよろしくお願いします。

0
引用返信 編集キー/
■8412 / inTopicNo.7)  Re[6]: SendMessageについて
□投稿者/ Blue 大尉(162回)-(2006/11/20(Mon) 15:08:07)

分類:[VB.NET] 

> しかしながら、私のスキル不足で受け側がよくわかりません。C++のサンプルを見たのですが理解不能です。
まぁ、C++のサンプルはわかんなくて当然だと思います。
ここら辺はIntPtrで受け渡しすることになるので、Marshal.〜を使ったことないとけっこう困難ですから。

Imports System
Imports System.Windows.Forms
Imports System.Runtime.InteropServices

Public Class Form1
Inherits System.Windows.Forms.Form

Private Const WM_COPYDATA As Integer = &H4A
Private Structure COPYDATASTRUCT
Public dwData As IntPtr
Public cbData As Integer
Public lpData As IntPtr
End Structure

Public Shared Sub Main()
Application.Run(New Form1())
End Sub

Public Sub New()
MyBase.New()

InitializeComponent()
End Sub

Private Sub InitializeComponent()
With Me
.Text = "Recv"
.Width = 100
.Height = 100
End With
End Sub

Protected Overrides Sub WndProc(ByRef m As System.Windows.Forms.Message)
If m.Msg = WM_COPYDATA Then
Dim cds As COPYDATASTRUCT

cds = CType(Marshal.PtrToStructure(m.lParam, GetType(COPYDATASTRUCT)), COPYDATASTRUCT)
MessageBox.Show(Marshal.PtrToStringUni(cds.lpData))
Else
MyBase.WndProc(m)
End If
End Sub

End Class


0
引用返信 編集キー/
■8420 / inTopicNo.8)  Re[7]: SendMessageについて
□投稿者/ すー 二等兵(7回)-(2006/11/20(Mon) 21:11:01)

分類:[VB.NET] 

Blue さま

大変ありがとうございます。
Marshal.〜はまったく使ったことがないので苦労しています。
おまけにVBのサンプルはぜんぜん見当たらないし・・・
あと1点、SendMessageの戻り値の設定について教えてください。
いろいろと調べていると受け側で戻り値を設定できるようですが、どのようにするのでしょうか?
受け側のWndProcでm.Result = New IntPtr(1)としましたがうまくいきません(戻り値:0)
お手数ですがよろしくお願いします。

0
引用返信 編集キー/
■8421 / inTopicNo.9)  Re[8]: SendMessageについて
□投稿者/ Blue 大尉(163回)-(2006/11/20(Mon) 22:47:42)

分類:[VB.NET] 

m.Result = CType(1, IntPtr)

としたらどうでしょうか?


ちなみに、WM_COPYDATAの戻り値は 1(成功) か 0(失敗) と決まっていますので。

0
引用返信 編集キー/
■8422 / inTopicNo.10)  Re[9]: SendMessageについて
□投稿者/ Blue 大尉(164回)-(2006/11/20(Mon) 22:58:46)

分類:[VB.NET] 

>m.Result = New IntPtr(1)
で試してみましたが、ちゃんと1が取得できますよ。

0
引用返信 編集キー/
■8426 / inTopicNo.11)  Re[10]: SendMessageについて
□投稿者/ すー 二等兵(8回)-(2006/11/21(Tue) 09:17:56)

分類:[VB.NET] 

Blue さま

大変申し訳ありませんでした。
WndProcのMyBase.WndProc(m)の位置を間違えていました。
if文の外に出していて必ず通るようになっていました。お恥ずかしい

今回の件、Blue さまのアドバイスがなければ・・・
感謝いたします。ありがとうございます。


解決済み
引用返信 編集キー/


トピック内ページ移動 / << 0 >>

このトピックに書きこむ

過去ログには書き込み不可

管理者用

- Child Tree -