|
Cyrilix wrote: Then my question is, how do you explain the current crop of games today? They don't update the frame buffer synchronously. They won't be trying to send you 60 frames per second all the time. On heavier scenes, the frames may drop down to the 20s, and on lighter scenes, they may jump up to 150. What else, besides a while loop displaying graphics would do this?
To make sure I understood correctly, I thought you were saying your graphics thread would literally have nothing to do until it recieved some sort of input, so it would do nothing but check an inbox, continuously, billions of times a second, until it recieved a message. This is pointless processing, even if you put in a seperate thread. If you're running a seperate *process* as opposed to thread, sometimes that sort of wait loop is necessary, but then you call Sleep() with each iteration to avoid wasting the CPU. A windows application behind the scenes has a message loop, but when it calls GetMessage, windows doesn't return until there is actually a message, so the calling process isn't wasting time continuosly checking.
AS far as modern games, I didn't think you were developing for PlayStation X or some specific game processor, but they can ascertain the game state (e.g. how many frames to display at a given time), without the sort of loop you're talking about.
Just to reiterate, I think the way to go for game state updates is a windows timer (don't know what the precise synax in MFC is).
|
|
|
|
|
Oh no, what I meant was... the graphics thread would be in a while loop constantly filling the frame buffer and putting it to the screen. On every iteration of filling this frame buffer, it would have to draw a bunch of shapes, and a set of variables that track your movement (say, x, y, z, and rotate), would determine how to redraw the scene. It would have to check these variables on every iteration. Basically, I'd have to know the translations and rotations that affect my camera every time I redraw.
The code would be very similar to what is on Nehe's OpenGL tutorial: Link to source
Here is the code that I'm pointing to, specifically:
while(!done)
{
if (PeekMessage(&msg,NULL,0,0,PM_REMOVE))
{
if (msg.message==WM_QUIT)
{
done=TRUE;
}
else
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
else
{
if (active)
{
if (keys[VK_ESCAPE])
{
done=TRUE;
}
else
{
DrawGLScene();
SwapBuffers(hDC);
}
}
if (keys[VK_F1])
{
keys[VK_F1]=FALSE;
KillGLWindow();
fullscreen=!fullscreen;
if (!CreateGLWindow("NeHe's OpenGL Framework",640,480,16,fullscreen))
{
return 0;
}
}
}
}
MODIFIED:
I guess my question is -- you would consider this bad design?
-- modified at 16:07 Monday 18th June, 2007
|
|
|
|
|
The code sample you provided is in a loop with a PeekMessage. If any messages for the application are pending it processes those before going back to frame updates.
Here was your proposed design:
Cyrilix wrote: I was thinking of using a key array (of bools) and catching WM_KEYDOWN / WM_KEYUP to change the states of the keys from the input thread, then sending the states to the graphics thread. The input thread would have the WndProc function, whereas the graphics thread would simply check the local key array (in a while loop) to determine what happens.
Basically, it would look sort of like this:
WndProc (which runs in the input thread) catches WM_KEYDOWN where the key is VK_ESCAPE. The input thread sets key[VK_ESCAPE] = true. The graphics thread has a while loop that checks for VK_ESCAPE, and if true, it will return the thread (quit), if it sees another command such as the movement keys, then it will draw the next frame.
You weren't relinquishing control in anyway to process application messages. However, I'm not entirely clear on your design, because your last statement seems to say that movement in the game is only triggered by user input, whereas I thought there would be game animation regardless of user input.
But as to whether the code sample you provided is bad design, I will say I've never had much use for PeekMessage. In the code sample, you could just take the PeekMessage portion out, and put the remaining code in its own thread, where the OS itself would interrupt it as necessary. The GetMessage loop in the main thread would continue to handle application messages. Maybe you can tell me if I'm missing something
l
|
|
|
|
|
There will have to be game animation regardless of user input. When I say "if it sees another command such as the movement keys, then it will draw the next frame", I mean that if it sees that you're holding down the movement key to move in direction x, it will increment an x counter (based on how long you've been holding down the key). The bit of code above that I posted will check this counter every time a frame is drawn (DrawGLScene()) and translate the camera x units from the (0, 0, 0) position (or rather, translate the objects -x, since it's the objects that are moving, and not you). The main point is, it uses a while loop to constantly spit out frames to the screen. I thought you were advocating against using the while loop and producing frames only when you receive a signal, but it seems like you're not against doing so.
We may have misunderstood each other.
|
|
|
|
|
I have a feeling I may not be completely clear to you.
In the code sample, he has something he feels he has to do continuously. In that instance just create a seperate thread, and do it continously, and let the OS interrupt - No need to call PeekMessage. However, this code doesn't create a seperate thread but is in the main thread, that's why PeekMessage is being used. (You OTOH were saying you wanted to create a seperate thread for graphics updates.) However, in your case, you seemed to say you had nothing to do in the Graphics thread until some user input was received, so you would have a loop to just check for it continuously. That's a complete waste.
|
|
|
|
|
The graphics thread always has something to do. It has to draw the frames, whether or not user input is entered. If no user input or no AI interaction (that results in a change of what you can see on the screen) is there, then it should just draw the same frame, and then keep on drawing frames forever after that.
First, I'd like to ask whether or not you're disputing my statement above, because everything I mentioned in the last few posts is in question to whether or not you dispute drawing frames continuously.
|
|
|
|
|
Cyrilix wrote: The graphics thread always has something to do. It has to draw the frames, whether or not user input is entered. If no user input or no AI interaction (that results in a change of what you can see on the screen) is there, then it should just draw the same frame, and then keep on drawing frames forever after that.
First, I'd like to ask whether or not you're disputing my statement above, because everything I mentioned in the last few posts is in question to whether or not you dispute drawing frames continuously.
I'm not sure if I dispute it. How do you control at what rate the frames are being updated? If on a given frame, nothing has changed, do you go ahead and redraw it anway? It seems you would only update at set time intervals (1/10 of a second or 1/100, whatever), in which case you could put the update code in the main thread and have it triggered by WM_TIMER messages. Or, if running continuously in a seperate thread, Sleeping for a set time interval on each iteration. Maybe the AI engine could be running continuously in a seperate thread, and when it was time for an update, you could query it, and it could give the best data it had at the moment.
------
I guess I need to read more carefully - you did say a frame is updated whether its changed or not. I would say it should be on a timer.
You did say you were a beginner. I have written a several thousand line long windows app that is fairly entertaining game that is a little more sophisticated than pac-man.
|
|
|
|
|
I see what you mean, although I'm unsure of the implementation, but I will look into what you've suggested a bit more before making my decision.
Thanks.
|
|
|
|
|
Most games today are single threaded, believe it or not. They work everything on a frame by frame basis so for each frame they render all the graphics, do some user input and sometimes use up the rest of the time until they have to do the next frame by doing some AI or some house keeping operations.
I have tried implementating a properly multithreaded game engine with rendering on one thread, game mechanics on another and yet another for sound. It's HARD to get the kind of performance pro games expect doing it that way. When quad core is standard it will come and my AG engine will rock
Nothing is exactly what it seems but everything with seems can be unpicked.
|
|
|
|
|
Hi Matthew,
After all this long discussion, I'm still trying to figure out, regardless of whether I use multiple threads or a single thread, whether or not using a while loop to continuously draw my scene as in the OpenGL example, is the right thing to do.
My fundamental design for single thread is very simple: Do the DrawScene loop and take the input before drawing the frame each time. If there is no input or no AI interaction, then it will just draw the same scene as it did last time.
My fundamental design for multiple threads is just as simple: Do the input loop in the input thread, do the DrawScene loop in the graphics thread, and have the DrawScene take the input before drawing the frame every time. If there is no input or no AI interaction, then it will just draw the same scene as it did last time.
|
|
|
|
|
|
Hi all...
Is it possible to mix more than one bitmap in VMR9 using MixerBitmap in one time? I've tried to create two IVMRMixerBitmap instances, two SetInitialAlphaBitmap functions (as in BmpMix9 example), but only the last one is displayed.
Thank you...
-Houari
|
|
|
|
|
IVMRMixerBitmap::SetAlphaBitmap() sets a new bitmap, replacing the previous one.
You can, however, combine your bitmaps into one bitmap
Mark
"Posting a VB.NET question in the C++ forum will end in tears." Chris Maunder
|
|
|
|
|
ah yes... that was in my mind too... ^^
but I need the position of my bitmaps in the video to be independently changed anytime I want.
is there any way to do this? I was also failed by using CDC in the same picture control with the vmr video (the CDC drawing is overlapped by the video...) -_-
thanks
-Houari
|
|
|
|
|
houari_id wrote: but I need the position of my bitmaps in the video to be independently changed anytime I want.
You'd need to redraw the offscreen bitmap each time the bitmaps change position.
If you're experienced with DirectDraw (I personally am not) you can also use the
VMR Renderless Playback Mode (Custom Allocator-Presenters)[^].
The alternative I chose was to make my own renderer filter so I had complete control over all the
drawing. That certanly isn't a necessary solution however.
houari_id wrote: I was also failed by using CDC in the same picture control with the vmr video (the CDC drawing is overlapped by the video...)
Yeah, that won't work well.. That's why mixing is necessary
Mark
"Posting a VB.NET question in the C++ forum will end in tears." Chris Maunder
|
|
|
|
|
Hi,
How could i code this fast in C++ by using classes:
I want to output the work days between two dates (start and end date input by user).
I thought through it but dont know how to code it.
My thoughts:
1) calculate (count up) the absolute days between the two dates (with using time.h and week modulo to find out the free Sundays)
2) make a class with holidays
3) calculate the holidays with the Gauss easter algorithm (found it on wikipedia and some other site, see bottom of post)
4) substract the holidays from the absolute days
5) "cout" the absolute days and the count up of holidays and the final work days
Carl Friedrich Gauß (1777 - 1854):
a = YYYY mod 19
b = YYYY mod 4
c = YYYY mod 7
d = (19a + M) mod 30
e = (2b + 4c + 6d + N) mod 7
YYYY: the year with 4 digits
M and N:
for 1583 - 1599 -> M=22, N=2
1600 - 1699 -> 22, 2
1700 - 1799 -> 23, 3
1800 - 1899 -> 23, 4
1900 - 1999 -> 24, 5
2000 - 2099 -> 24, 5
2100 - 2199 -> 24, 6
2200 - 2299 -> 25, 0
2300 - 2399 -> 26, 1
2400 - 2499 -> 25, 1
taking the above easter sunday should be: (22 + d + e).March or (d + e - 9).April
and there are 2 annomalies:
1) if the result of the above falls on the 26th of April -> easter sunday will be held on the 19th of April instead
2) If a > 10 and d = 28 and the result the 25. April, -> easter sunday be corrected to the 18. April.
but how to code this?
HELP
thx a lot
berni2k
|
|
|
|
|
berni2k wrote: but how to code this?
Indeed. That sound like a very interesting class assignment. Good luck.
|
|
|
|
|
thx, I am on the way and will post the code if i can manage to do it
|
|
|
|
|
Hello, I have two questions about the stack.
1st)In MS visual studio the stack is 1MB as far as I now.
I found that using a recursive function the stack overflows at depth ~4900.
Why does this happen?
2nd)If someone has a linked list with thousand of elements how he can
reach the whole list using a recursive function?
thanks.
|
|
|
|
|
Lord_Vader wrote: 1st)In MS visual studio the stack is 1MB as far as I now.
Lord_Vader wrote: Why does this happen?
When you reach the limit, regardless of what that is, you get the overflow error. What is so hard to understand about that?
Lord_Vader wrote: 2nd)If someone has a linked list with thousand of elements how he can
reach the whole list using a recursive function?
Why would you want to do that?
|
|
|
|
|
1st)Its not hard to understand that.
But I want someone to explain specifically what happens, for example how much stack
memory one function call consumes why...
2nd)Because I have a linked list with thousand elements and I wondering if it is
possible to go through it using recursive functions.
|
|
|
|
|
Why would you iterate through a linked list with a recursive function? You already figured out the answer to your question: it is not possible unless you increase the stack size, since you seem to top at around 4900.
Just call the next pointer until you reach the end of the list. It only takes a single function.
|
|
|
|
|
Ok thanks,I was going to do that,
but I posted mainly to learn the details behind a functions call..
|
|
|
|
|
Stack memory is generally required for the function call information (return values and return address), as well as for the automatic variables in the function being called. One function may consume only 32 bytes of stack while another consumes more than 8KB of stack.
It is possible to recursively iterate over any size list... Given you have enough stack space and your environment supports it. Realistically, this depends on (1) how much stack is consumed by the recursive function, (2) how many elements are in the list, and (3) how much free stack space you have remaining at the time you start recursion (just because you have 1MB of stack by default in Win32, that does not mean that by the time your function is first called that you will have much of it left).
Iteration is generally better done using loops instead of recursion. It is also easier to debug, because you can more easily break at a certain loop counter than a certain recursion depth.
Peace!
-=- James Please rate this message - let me know if I helped or not!<HR> If you think it costs a lot to do it right, just wait until you find out how much it costs to do it wrong! Avoid driving a vehicle taller than you and remember that Professional Driver on Closed Course does not mean your Dumb Ass on a Public Road! See DeleteFXPFiles
|
|
|
|
|
Thanks,
Here is another one.
I additionally have a bin tree with many thousands of elements.
I use recursive functions to walk through the leafs because its more intuitive.
Will it be faster if I use loops instead?
|
|
|
|
|