'Getting terminal input with SDL window open?

I'm trying to make a program that makes use of an SDL Window, this window is invoked through an object that will contain functions to do on the window.

The issue I'm having is that I want to take input through the terminal, which in turn will call commands for the object to complete.

I've tried using multithreading but I've found I need the instance of the class both in the main and in the SDL Thread, a way to fix this would be a global class instance but I think this would be bad programming.

Is there any other way to have an SDL Window open and do things such as cin within the terminal window



Solution 1:[1]

It's good practice to make auxiliary threads for I/O purposes as simple as possible. Have your main thread handle all the logic, and make a thread that pushes values to a mutexed stack. The main thread can then pop any values off the stack and react to it accordingly. Since you're working with a console, you can't have concurrent inputs, so a stack isn't needed. Here's a simple example. While I don't have a working toolchain on this computer, this seems like it ought to work.

#include<string>
#include<sdl/sdl.h>
#undef main //I HATE SDL FOR REDEFINING MAIN

class asynccin{
    static std::string val;
    static int hasval;
    static void thread(void*a){
        cin >> val;
        hasval = 2;
    }
    public:
    static bool begininput(){
        if( hasval != 0 ) return false;
        hasval = 1;
        SDL_CreateThread( thread, NULL );
    }
    static bool hasinput(){
        return hasval == 2;
    }
    static std::string reapinput(){
        hasval = false;
        return val;
    }
};

int main{}{

    //init SDL
    while( true ){
        //loop stuff
        asynccin::begininput();
        if( asynccin::hasinput() ){
            cout << asynccin::reapinput();
        }
    }
}

Solution 2:[2]

Got an example working! A few functions needed to return a bool, and the static variables have to be declared, not just defined. Besides that, Kaslai's answer works like a charm!

class asynccin{
    static std::string val;
    static int hasval;
    static int thread(void*a){
        std::cin >> val;
        hasval = 2;
        return 0;
    }
    public:
    static bool begininput(){
        if( hasval != 0 ) return false;
        hasval = 1;
        SDL_CreateThread( thread, "ConsoleInput", (void *)NULL );
        return true;
    }
    static bool hasinput(){
        return hasval == 2;
    }
    static std::string reapinput(){
        hasval = false;
        return val;
    }
};
int asynccin::hasval = 0;
std::string asynccin::val = "";

int main{}{
    //init SDL
    while( true ){
        //loop stuff
        asynccin::begininput();
        if( asynccin::hasinput() ){
            cout << asynccin::reapinput();
        }
    }
}

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1
Solution 2 Kanor