Jump to content

View more

Image of the Day

Boxes as reward for our ranking mode. ヾ(☆▽☆)
#indiedev #gamedev #gameart #screenshotsaturday https://t.co/ALF1InmM7K
IOTD | Top Screenshots

The latest, straight to your Inbox.

Subscribe to GameDev.net Direct to receive the latest updates and exclusive content.


Sign up now

Getting raw keyboard input in console programming using Linux

4: Adsense

Old topic!

Guest, the last post of this topic is over 60 days old and at this point you may not reply in this topic. If you wish to continue this conversation start a new topic.


  • You cannot reply to this topic
5 replies to this topic

#1 Edvinas Kilbauskas   Members   

1167
Like
0Likes
Like

Posted 16 October 2013 - 02:27 AM

So I thought I would develop tetris game in C on linux. Everything works fine, except I can't find a way to get input without interrupting whats going in my game. My game has main loop which I don't want to stop. So regular console input methods don't work. I also tried to open /dev/input/eventX and read keyboard state from there, but it doesn't seem to read anything, but if I do "cat /dev/input/eventX" it does show that it contains events. 

I also tried using glut and glutKeyboardFunc, but that doesn't seem to work either. As it probably needs a focused X window to operate.

 

Does anyone have any ideas what could I try next? 


“There are thousands and thousands of people out there leading lives of quiet, screaming desperation, where they work long, hard hours at jobs they hate to enable them to buy things they don't need to impress people they don't like.”― Nigel Marsh

#2 TheComet   Members   

3859
Like
0Likes
Like

Posted 16 October 2013 - 03:38 AM

Reading from /dev/input/eventX should work, perhaps if you share your code we can help pinpoint the problem?

 

Otherwise, have you checked out one of the console UI libraries such as ncurses?


"I would try to find halo source code by bungie best fps engine ever created, u see why call of duty loses speed due to its detail." -- GettingNifty

#3 Álvaro   Members   

20912
Like
0Likes
Like

Posted 16 October 2013 - 07:40 AM

There are other options, like SDL. What are you using for graphics? Or does your program run in a terminal?



#4 lprog101   Members   

101
Like
0Likes
Like

Posted 16 October 2013 - 08:50 AM

You need to create a separate thread to handle the keyboard input, and feed that to your main loop when the data is ready. You can use fork() or posix threads.

This way your main loop never stops, but only processes data when it is available.

You can feed the data from the child thread in a few ways.... pipe is OK, google how to do it. You can also set up shared memory, I think posix threads have apis to support.

I would really start with fork() as it clarifies the concept, posix threads are good but more complex.

Good luck! And have fun, sounds like a great Linux programming 101 topic!

#5 Álvaro   Members   

20912
Like
0Likes
Like

Posted 16 October 2013 - 08:58 AM


You need to create a separate thread to handle the keyboard input, and feed that to your main loop when the data is ready [...]

 

That is good advice if you want to process entire lines of text, like you would when implementing a chess engine that communicates with a GUI using text. However, this won't do you any good for tetris, which is what the OP is writing.



#6 Zimans   Members   

237
Like
0Likes
Like

Posted 18 October 2013 - 06:29 AM

Are you just trying to read from the device raw? You need to read events:

 

Quick hack cut+paste from another project:

        int fd = ::open( "/dev/input/event0", O_RDONLY | O_CLOEXEC );
        if( -1 == fd )
            return false;
        char name[ 32 ];
        if( -1 == ioctl( fd, EVIOCGNAME( sizeof( name )), name ))
            return false;
        
        // Grab input
        if( -1 == ioctl( fd, EVIOCGRAB, (void*)1 ))
        {
            printf( "Failed to grab input %s: (%i) %m", name, errno );
            return false;
        }

	struct input_event ev;
	memset( &ev, 0, sizeof( ev ));
	if( -1 == read( m_input, &ev, sizeof( ev )) )
	{
		printf( "read() failed: (%i) %m", errno );
		return;
	}
	
	if( ev.type != EV_KEY ) return;
	if( ev.value != 0 ) return;

	if( ev.code == KEY_F11 )
		next_channel();
	else if( ev.code == KEY_F12 )
		display().show_osd( !display().osd_visible );

You will want to enable non blocking, then handle the EAGAIN when the read fails.

 

-Z






Old topic!

Guest, the last post of this topic is over 60 days old and at this point you may not reply in this topic. If you wish to continue this conversation start a new topic.