わびさびサンプルソース

WindowsやHTML5などのプログラムのサンプルコードやフリーソフトを提供します。

スレッドにメッセージを送信する

スレッドにメッセージを送信するには、PostThreadMessage()関数を使用します。 スレッド側でメッセージを受信するには、PeekMessage()関数であらかじめメッセージキューを生成しておく必要があります。 PeekMessage()関数でメッセージキューを生成するまでは、メッセージを受信することができませんので、 イベントなどを利用して、メッセージキューが生成されたことを確認してから送信する必要があります。

スレッドの終了コードを取得する
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
#include <stdio.h>
#include <tchar.h>
#include <iostream>
#include <string>
#include <process.h>
#include <windows.h>
 
 
 
/*
    スレッドメイン処理
*/
unsigned __stdcall ThreadMain
(
    void* vpArguments
)
{
    /*
        スレッドの起動引数に、初期化完了イベントをのせています
    */
    HANDLE hThreadInitEvent = (HANDLE)vpArguments;
 
    // メッセージ
    MSG oMsg;
 
    // メッセージキューの作成
    ::PeekMessage( &oMsg, NULL, 0, 0, PM_NOREMOVE );
 
    // スレッド初期化完了(メッセージキュー生成完了)
    ::SetEvent( hThreadInitEvent );
 
    std::wcout << L"スレッド開始( 引数 = " << (int)vpArguments << L" )" << std::endl;
 
 
    /*
        スレッドメイン処理
            (GetMessageは、WM_QUIT以外を受信すると0以外の値が返ります)
    */
    while( 0 != ::GetMessage( &oMsg, NULL, 0, 0 ) ) {
        switch( oMsg.message ) {
        case WM_USER + 0x100:
            {
                std::wcout << L"メッセージを受信しました(WM_USER + 0x100)。( " << oMsg.wParam << L" )" << std::endl;
            }
            break;
 
 
        case WM_USER + 0x101:
            {
                std::wcout << L"メッセージを受信しました(WM_USER + 0x101)。( " << oMsg.wParam << L" )" << std::endl;
            }
            break;
        }
    }
 
 
    /*
        スレッドの終了
            この値はGetExitCodeThread()で取得できる
    */
    std::wcout << L"スレッド終了" << std::endl;
    ::_endthreadex( 1234 );
 
    // 処理結果
    return( 0 );
}
 
 
 
/*
    スレッドの終了コードを取得する
*/
int _tmain
(
      int argc
    , _TCHAR* argv[]
)
{
    /*
        std::wcoutのロケールを設定
         これを設定するだけで、std::wcoutで日本語が表示される
         ようになります。
    */
    std::wcout.imbue( std::locale( "", std::locale::ctype ) );
 
    UINT nThreadId = 0;
 
 
    /*
        スレッド初期化完了イベントの生成
    */
    HANDLE hThreadInitEvent = ::CreateEvent(
              NULL      // SECURITY_ATTRIBUTES構造体
            , TRUE      // リセットのタイプ( TRUE: 自動 / FALSE: 手動 )
            , FALSE     // 初期状態( TRUE: シグナル状態 / FALSE: 非シグナル状態 )
            , NULL      // イベントオブジェクトの名前
        );
 
 
    /*
        スレッド起動
    */
    HANDLE hThread = (HANDLE)::_beginthreadex(
              NULL                      // SECURITY_ATTRIBUTES構造体
            , 0                         // スタックサイズ( 0は呼び出し側と同じサイズ )
            , &ThreadMain               // スレッド関数
            , (void*)hThreadInitEvent   // スレッド関数への引数
            , 0                         // 作成オプション( 0 / CREATE_SUSPENDED )
            , &nThreadId                // スレッドId
        );
    std::wcout << L"スレッド起動 Id = " << nThreadId << std::endl;
     
 
    /*
        スレッドの初期化待ち(スレッドにメッセージキューが出来るまで待つ)
            → メッセージキューが生成されないとメッセージが送れません
    */
    ::WaitForSingleObject( hThreadInitEvent, INFINITE );
 
    // スレッド初期化イベントの破棄
    ::CloseHandle( hThreadInitEvent );
 
 
    /*
        スレッドへメッセージを送信する
    */
    for ( UINT nI = 0; nI < 10; nI++ ) {
 
        // メッセージの送信
        ::PostThreadMessage( nThreadId, WM_USER + 0x100, nI, 0 );
 
        // 待ち(待たなくても良い → 適当です)
        ::Sleep( 1000 );
 
        // メッセージの送信
        ::PostThreadMessage( nThreadId, WM_USER + 0x101, nI, 0 );
 
        // 待ち(待たなくても良い → 適当です)
        ::Sleep( 1000 );
    }
 
    // スレッド終了メッセージの送信
    ::PostThreadMessage( nThreadId, WM_QUIT, 0, 0 );
 
 
    /*
        スレッドの終了待ち
    */
    ::WaitForSingleObject( hThread, INFINITE );
 
    // スレッド終了コード
    DWORD dwExitCode = 0;
 
    // スレッドの終了コードを取得
    ::GetExitCodeThread( hThread, &dwExitCode );
 
    std::wcout << L"スレッド終了コード( " << dwExitCode << L" )" << std::endl;
 
    // スレッドハンドルの解放
    ::CloseHandle( hThread );
 
    // 処理結果
    return( 0 );
}

実行結果

スレッド起動 Id = 12864
スレッド開始( 引数 = 212 )
メッセージを受信しました(WM_USER + 0x100)。( 0 )
メッセージを受信しました(WM_USER + 0x101)。( 0 )
メッセージを受信しました(WM_USER + 0x100)。( 1 )
メッセージを受信しました(WM_USER + 0x101)。( 1 )
メッセージを受信しました(WM_USER + 0x100)。( 2 )
メッセージを受信しました(WM_USER + 0x101)。( 2 )
メッセージを受信しました(WM_USER + 0x100)。( 3 )
メッセージを受信しました(WM_USER + 0x101)。( 3 )
メッセージを受信しました(WM_USER + 0x100)。( 4 )
メッセージを受信しました(WM_USER + 0x101)。( 4 )
メッセージを受信しました(WM_USER + 0x100)。( 5 )
メッセージを受信しました(WM_USER + 0x101)。( 5 )
メッセージを受信しました(WM_USER + 0x100)。( 6 )
メッセージを受信しました(WM_USER + 0x101)。( 6 )
メッセージを受信しました(WM_USER + 0x100)。( 7 )
メッセージを受信しました(WM_USER + 0x101)。( 7 )
メッセージを受信しました(WM_USER + 0x100)。( 8 )
メッセージを受信しました(WM_USER + 0x101)。( 8 )
メッセージを受信しました(WM_USER + 0x100)。( 9 )
メッセージを受信しました(WM_USER + 0x101)。( 9 )
スレッド終了
スレッド終了コード( 1234 )






わびさびサンプルソース

WindowsやHTML5などのプログラムのサンプルコードやフリーソフトを提供します。