Please explain why...

Started by
6 comments, last by clabinsky 21 years, 4 months ago
I always seem to hear that the flow of the game loop should roughly be: 1. handle input 2. render one frame What interests me is the separation of the two, forget AI and such for now. I have built a window GUI in directx and I am not following this rule as far as I can see. In the system I have done, the surfaces are updated depending on the input. For example, when WM_MOUSEMOVE is called, I update a variable with the new mouse position and call a function which handles mouse moves. This function checks a list of windows and calls the mouse move function of the window that should handle the event. Now, the window itself checks its subwindows (controls) and determines if the event should update anything. If a control of the window shoudl react to the event it does so immidiately. Say for example a button which just got the mouse pointer on top of it. It should change the current bitmap of the button. It does so by blitting the new bitmap to the parent window''s off screen surface and returns to the calling function of the parent window. Since the parent window is usually an offscreen surface, it will blit itself to the backbuffer if needed, before returning. If there are no other messages, the backbuffer will be flipped. Now, isn''t this both handling input and rendering at the same time? Any other comments re efficiency would be greatly appreciated. Claes
Why make it simple when you can make it sooo nice and complicated?
Advertisement
BUMP Anyone?
Why make it simple when you can make it sooo nice and complicated?
i really wouldnt compare typical games with windows apps. the apps use a lot of messages to call functions and do stuff when its needed, while a game doesnt need messages at all (even though they are useful for a lot of things).
f@dzhttp://festini.device-zero.de
I''m not sure I agree.

This is a game by all means. Fullscreen mode with directX. Turn based strategy.

However, I use a window system to display messages and data. Since there is not much animation, the frames does not get updated as often as in a real time game for example.

I currently do not have any messages sent between the windows, it is just a matter of finding where a certain input goes and what should be done.

Appreciate you answer, but I am still eager to know if the event model in which an event such as a mouse move would end with a blit to the screen instead of handling the event by setting variables and separately blit everything to the buffer. The problem I see with this is that you''d have to have some kind of flag which tells what should be updated unless every frame is built from scratch, which I think would be inefficient.

What you say?

Claes
Why make it simple when you can make it sooo nice and complicated?
I think the trick is that in most games, the whole screen is moving. You''re not just updating a little window here or there when someone clicks something, you''re moving the whole world around. Consider something like a first person shooter. If you turned your head and fired, while other people were moving around and firing all within one typical frames worth of time your rendering process would look something like this:

You turn: Re-render the whole screen
You fire: Render shot...but there''s transparency, so render all the areas it touces.
Someone moved: Render all the area he coverd.
Somone else moved and fired: Render, render, render some more.

As you can see, with the whole scene moving around it ends up being quite inefficient to update your rendering based off of events that happen. If you went about it this way you would most likely end up lagging down whenever the action got fierce, which is not what you want. To compound the problem, if you get stuck in a large event loop of updates then you may miss important input from the user.

Instead, most games use a model where they catch up on all the input and things going on and then render a snapshot of what''s happening. This process is then just repeated over and over. In this way, you get a constant stream of steady(theoretically) action, instead of the hiccups that would be caused by event based updates.

For a turn based strategy game like you''re doing, it probably won''t matter a bit. But if you started to work on a game like Mario, Quake, etc. then I think you''d see the effects of it right away.

-John
- John
*g* so to save my answer: your windows strategy game isnt what i meant with ''typical game'' ,-)
if you dont have a thousand things that require an update the ''windows way'' is fine, for the example above it would mean to render dozens of frames instead of just one.

so my answer is valid only for typical ''endless game-loop'' games, not for ''endless message-loop'' games *g*
f@dzhttp://festini.device-zero.de
You''re not working with a frame-based system, so handling things in a different way makes sense. But, be wary about coupling things too tightly, as it makes for code that will be difficult to maintain.

[ MSVC Fixes | STL | SDL | Game AI | Sockets | C++ Faq Lite | Boost | Asking Questions | Organising code files | My stuff ]
Got you Trience.
You too Teknofreak,
and Kylotan.

I suspect this should be in the Software Engineering thread after these mails.

Yes coupling is a real challenge to avoid, and I think I have.

But, I see a need to change this to a frame based system. Even though the rendering is not especially heavy, there are a lot of calculations being done and I need to make things as efficient as possible.

Now, separating the input and the rendering make sense. To change my system I need to be able to render a window based on its current state. Doing this by re rendering the whole frame is easy but a lot of wasteful blitting. I have been thinking about the implemenentation half the night and have an idea.

First, the reason the current solution is slow is because each event taken from the message pump takes too long to handle because of the number of steps and the blitting?
Q1. Right so far?

Second, by separating the rendering and input, each event will basically just change the state of one or more objects.
Q2. Am I right so far?

Third, as soon as there are no more messages to handle, a list of objects (explanation follows) will be rendered and the backbuffer will be flipped.

Q4. Lets assume there are many messages to take care of. This could potentially cause the game to jump forward so to say by allowing many changes to the state of the objects before rendering the next scene. Wont be much of a problem in my case but anyway. Right?


The game loop:

  	while(true)	{		if(PeekMessage(&msg,NULL,0,0,PM_REMOVE))		{			if(msg.message==WM_QUIT) 				break;			TranslateMessage(&msg);			DispatchMessage(&msg);		}		else		  cGame->Run();	};  


I see some problems with this loop when there are many messages to handle but thats another story.

Idea:
Each window contains controls which needs to be updated as the user clicks, moves the mouse etc. When I set the state based on an event, the object that needs to be re rendered, attaches itself to the top of the render queue. After messages are processed the render queue is rendered from bottom an up. This seems fine until I realize that one object might potentially have to be re rendered twice. Sure, it should still work but it is one rendering too much since only the snapshot of the last state will be shown. I think I might have to change the structure of the game even more.

I would very much appreciate some ideas on the above.

Regards,
Claes
Why make it simple when you can make it sooo nice and complicated?

This topic is closed to new replies.

Advertisement