リストボックスのサブクラス化によるlParamメッセージ

解決


井上  2006-05-25 18:23:52  No: 95495

はじめまして、井上です。
自アプリケーションのリストボックスのサブクラス化による
LB_ADDSTRING(リストボックスに追加)時のlParamメッセージを
文字列として拾いたいのです。
いろいろ試しているのですが、アプリケーションが落ちるなどして
うまくいきません。
以下はサブクラスのプロシ−ジャです。
lParamのロング値は構造体のポインタ?文字列のアドレスではない?
混乱しています。
どうか、お力添えをお願いいたします。

Public Function WindowProc(ByVal hWnd As Long, ByVal uMsg As Long, ByVal wParam As Long, ByVal lParam As Long) As Long

    Select Case uMsg
        Case LB_ADDSTRING
            Dim DD As String
            DD = String$(255, Chr(0))
            Call MoveMemory(DD, ByVal lParam, Len(DD))
            Form1.List2.AddItem Replace(DD, Chr(0), "")'別リストボックスに追加

    End Select

WindowProc = CallWindowProc(SubC, hWnd, uMsg, wParam, lParam)

End Function


井上  2006-05-25 18:32:05  No: 95496

すみません。

開発環境ですがVB6.0
Windows XP です。

肝心な事を忘れるなんて・・
申し訳ありません。


Blue  2006-05-25 18:50:29  No: 95497

lParamの値はきちんと入っているのですよね?

もしかしたら、Unicode文字列かもしれないので、MoveMemoryのDeclare宣言によりますけど、
> Call MoveMemory(DD, ByVal lParam, Len(DD))

Call MoveMemory(ByVal StrPtr(DD), ByVal lParam, Len(DD))
とするとうまくいくかも。


井上  2006-05-25 19:13:15  No: 95498

Blueさんありがとうございます。恐縮です。
VC++板でも、いつも勉強させていただいてます。

おかげさまでできました。StrPtrで受けるといいのですね。

MoveMemoryの宣言はAnyで受けていました。
Private Declare Sub MoveMemory Lib "kernel32" Alias "RtlMoveMemory" _
         (Destination As Any, Source As Long, ByVal Length As Long)

Public Function WindowProc(ByVal hWnd As Long, ByVal uMsg As Long, ByVal wParam As Long, ByVal lParam As Long) As Long

    Select Case uMsg
        Case LB_ADDSTRING
            Dim DD As String
            DD = String$(255, Chr(0))
            Call MoveMemory(ByVal StrPtr(DD), ByVal lParam, Len(DD))
            DD = StrConv(Left$(DD, InStr(1, DD, Chr(0), 1)), vbUnicode)
            Form1.List2.AddItem DD '別リストボックスに追加

    End Select

WindowProc = CallWindowProc(SubC, hWnd, uMsg, wParam, lParam)

End Function

本当にありがとうございました。


井上  2006-05-26 07:06:32  No: 95499

DD = StrConv(Left$(DD, InStr(1, DD, Chr(0), 1) - 1), vbUnicode)

後の人のために一応訂正m(_ _)m


Blue  2006-05-26 08:05:55  No: 95500

あれ?よく考えると、
> Call MoveMemory(DD, ByVal lParam, Len(DD))
Call MoveMemory(ByVal DD, ByVal lParam, Len(DD))
なのかも。


井上  2006-05-26 20:13:52  No: 95501

Blueさんありがとうございますm(_ _)m

VB6.0で作ったActiveX DLLとVC++.NET2003で作ったWin32 DLLで
メインアプリのリストビューにフォルダ&ファイルをアクティブに
表示しようとしています。
それを一旦メインアプリのリストボックスをSendMessageで追加したり
削除したりして管理することにより、サブクラスプロシージャから
リストビューアイテムを追加したり削除したりします。

Private Declare Function SendMessage Lib "USER32" Alias "SendMessageA" _
                (ByVal hWnd As Long, ByVal wMsg As Long, ByVal wParam As Long, lParam As Any) As Long

Call SendMessage(AnyListHwnd, LB_ADDSTRING, 0&, ByVal AddString)

送信した文字列を受信するのに手こずってました。
送信文字コードを変えてみたり、API宣言のlParam As Anyを明示的に
lParam As Stringとしてみたり。

今回の場合
Call MoveMemory(ByVal DD, ByVal lParam, Len(DD))
だとどうしてもメインアプリがどうしても落ちてしまうんです。
BlueさんのStrPtrで受ける以外どのパターンも失敗してしまいます。
うーむもう少し理解できるまで考えて見ます。


※返信する前に利用規約をご確認ください。

※Google reCAPTCHA認証からCloudflare Turnstile認証へ変更しました。






  このエントリーをはてなブックマークに追加