[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Beta Version - Please help



"Philipp Gühring" wrote:

> The first thing I need is delay(long n).
> delay should wait for n milliseconds. (thousands of a second)

man 3 usleep should enlighten you about that.

> The next thing I need is a constant framerate for my video player (it
> plays .flc and .fli videos) I need for example 15 frames per second.
> So the loop algorithm I wrote was the following:
> 
> Save the current time
> Load the frame
> Show the frame
> And now wait until the current time >= saved time+ 1/15 second
> Repeat the whole thing until all frames are shown.
> 
> How can I realize this timing strategy in Linux?

Your algorithm is okay, if you don't need to do anything else at the
same time (your game seems pretty simple, so I guess this isn't the
case). Use gettimeofday to get the current time and usleep to wait the
required number of microseconds (I think you can't count on this having
more than 10 millisecond of precision BTW).

> While playing the above way, it should be possible to skip the video
> or a sequence of videos by pressing a key on the keyboard. I realized
> this under DOS with kbhit(), which i couldn´t find in Linux.
> (kbhit is a non-blocking getch)

Then you should use poll() instead of simply usleep().

What you do is that you poll() the stdin fd (file descriptor) for input
(events field set to POLLIN|POLLPRI) and set a timeout in millisecond.
So what will happen is that poll will wait for input on the specified fd
up to the number of millisecond you specified, just what you are looking
for.

If it returns 0, there was no input, the timeout just expired, -1 means
an error (look in errno) and a positive number means something happened
to the fds you passed in.

For a more complicated game, you can put a large number of fds in there
to check for multiple sources of input. For example, if you decide your
game has a timebase of 10 ms, you can have your event loop always go
into a poll with the appropriate timeout and put all your fds in there
(network sockets, pipes, input, files). Then you can use this as a
cooperative scheduler, by making sure all your fds are set in
non-blocking mode and that you never read or write too much data at a
time. Then your loop will be able to know who's ready to write again,
who's ready to read again, thus keeping the program very responsive.

If you think that poll() looks like select(), well you are mostly right.
poll is a newer version of select. On kernel that have the poll system
call, poll checks just the fds you tell him to check (select checks a
range of fds, so if you check two fds, 4 and 6420, the kernel will scan
6416 fds for no good reason!). If the kernel doesn't have the poll
system call, the C library emulates poll using select.

I find it simpler to use, too.

> And the last thing is the Background music. I just forked and updated
> mikmod in the background, but it is still playing, when I stop the
> program with CTRL+C.

You can grab the SIGINT signal with sigaction, making sure you use the
SA_ONESHOT flag, then in the signal handler, you kill(2) the mikmod
subprocess (you need to have saved the pid for this). You should use the
same signal that you got (SIGINT), so that this is consistent. Lastly,
you raise(SIGINT).

Hope that helps!

-- 
Pierre Phaneuf
Ludus Design, http://ludusdesign.com/
"First they ignore you. Then they laugh at you.
Then they fight you. Then you win." -- Gandhi