[C++] 356 ChatGPTアプリの製作 その41 FLTKマルチスレッド化 promise, future

[Mac M2 Pro 12CPU, Sonoma 14.3.1, clang++ 15.0.0, FLTK 1.3.8]

ChatGPTアプリのアップデートは久々です。

cURL通信を中断する機能を実装するため、マルチスレッド対応に着手しました。

まずはリクエストの送信を別スレッドにしてデタッチ(切り離し)するようにしました。

これまでは受信があるまでGUIが固まっていたのが、他のボタンを押したりできるようになります。

ただし別スレッドの動作が終わってもその信号をGUIが受け取ることはできないため、システム音で知らせるようにしました。システム音が聞こえると自分でカーソルを少し動かして、メインスレッドに戻します。メインスレッドに戻るとリクエストの結果がGUIに表示されます。

次は中断ボタンを押すとコールバック関数で受信をabortするようにします。

#include <thread>
#include <future>

void sendCB(Fl_Widget*, void* data, std::promise<void>&& p) {

    <中略>

    p.set_value();
}

void sendCBWrapper(Fl_Widget* w, void* v) {
    // promiseとfutureを作成
    std::promise<void> p;
    std::future<void> f = p.get_future();
    
    // sendCBを新しいスレッドで実行し、promiseを渡す
    std::thread([w, v, p = std::move(p)]() mutable {
        sendCB(w, v, std::move(p));
    }).detach();
    
    // 別のスレッドでfutureの結果を待機
    std::thread([f = std::move(f)]() mutable {
        f.wait(); // sendCBの終了を待機
        std::system("afplay /System/Library/Sounds/Submarine.aiff"); // システム音を鳴らす
        cout << "sendCB終了" << endl;
    }).detach();
}