EventManager

Started by
11 comments, last by Cybrosys 20 years, 9 months ago
I've always wanted to know a good way of handling input and translating it into the game smart and easy (May sound wrong but by handling input I was more focused on where to put the keydown checks etc not how to handle input). Sure you could just check if the key was pressed etc at different places but I feel that its pretty god damn ugly and nasty. So I thought about writing an EventManager. I would bind for example Space to an enumerator, lets say PlayerEvents and rolled it to Player_Jump and each frame that key was checked to be pressed or held down or whatever the flag is set to, it will place that enumerator into an event vector. I have a function that gets the list of all the enumerator events that have been sent to the event manager and will alow the coder to handle them. Then as usual when writing something new you come up with something, why not just use the already existing windows messaging system instead of writing your own? Ideas? Suggestions? [edited by - Cybrosys on May 27, 2003 9:12:37 PM]
Advertisement
The standard Windows messaging system is, in general, not a good choice for games due to its speed (or lack thereof). Actually, my favorite way to handle input is similar to DirectInput''s mapping scheme. You would "poll" the input devices and have an array that maps each key/axis to an action and sets the correct bit or variable in an action array. Next, inside your main game code you can just test if the user requested each action. However, the system you proposed (placing every new action into a vector and only processing those) might be beneficial as well. The advantage to this scheme is that several keys can be mapped to the same action and that in-game you process actions intead of keystrokes, which makes a lot more sense. But overall, this seems similar to your plan I suppose

Danny
h20, member of WFG 0 A.D.
Lets take q1 for example, you bind a key to a certain command, say +jump. What is that exactly? Each time i press the space-key a +jump message is sent but to where and how is it managed? Thats what I would like to know. That was what I was trying to copy be creating an event manager.

Each frame I would run through each input device and check if any of the keys are down etc and if so is there a message binded to that key. If so then send that message of to the EventManager that stores the event untill next frame when the event will be handled.
I like that idea... basically, your abstracting what the input action does (i.e. jump/fire/etc...) from what the input action is (press of a key/button/etc...). Makes sense and shouldn't be too hard to do.

[edited by - Mage2k on May 28, 2003 1:08:35 PM]
---------------------------------------------------There are 10 kinds of people in the world:Those that understand binary, and those that dont...Mage
HL uses this kinda system and i gather from the way it works the setup is this :

on start up build a table of actions -> function bindings ("+jump" -> IN_Jump() for example)
The parse the config files and where you see +Jump you bind the input so that when that key is pressed the function IN_Jump() is called.

Might need a bit of refine ment but you get the general idea.
The intresting thing about this system is that if your binding code and calling code was reasonably abstract you could in theory set the whole thing up with a script and completely change how the game works.
There is an article on this very site which discusses binding input devices to user customizable controls. It even allows for key combos and constant (unchangeable) controls. Look here.

pan narrans | My Website | Study + Hard Work + Loud Profanity = Good Code
Minister of Propaganda : leighstringer.com : Nobody likes the man who brings bad news - Sophocles (496 BC - 406 BC), Antigone
q1 key presses:

Press Key
|
insert command for keypress from
key binding table into the command buffer
(the one you also use for console input)
|
The command buffer is executed and cleared
the next frame.

you can execute all key events directly in
the console, by typing in the command a key
is bound to.
In my engine I can specify a Lua script function for any key (or key combination including shift/ctrl etc). I think it's fairly funky, though I'm sure there are limitations. For example, I do:

Input:BindInput("GlobalMap", "esc", "ToggleExit")

Then when you press Escape when the GlobalMap is active, the Lua function ToggleExit is called with a value of 1 or 0 as a parameter depending on whether you pressed or released the key. Also I can do:

Input:BindInput("GlobalMap", "mousex", "Yaw")

So when you move the mouse, the Yaw Lua function is called, with the distance the mouse moved in screen pixels as a parameter.

To show the key combination:

Input:BindInput("GlobalMap", "lctrl a", "ToggleAbout")

So when I press left control and the a key, the ToggleAbout function is called.

[edited by - stodge on May 29, 2003 4:00:47 PM]
---------------------http://www.stodge.net
DirectInput has a feature built in that does what you want (if I understood it corerctly). They''ve called it "action mapping". If you have the SDK, check the docs, or if not then search msdn/directx section.

:::: [ Triple Buffer V2.0 ] ::::
[size=2]aliak.net
The hole thing is i''m trying to write my code entirely oop. This means that there will be no functions outside classes. Binding functions by using void points isnt doable if the function is in a class. The program has no way of telling if the functions memory address is correct because it doesnt know if the class has been alocated. That''s why I couldnt just have a list of void pointers or such binded to keys since all the functions are inside classes. If I try the compiler will get mad

In any case I finished my CEventManager and CInputManager to a certain degree so that I could test it. Right now it only supports keyboard bindings. I bind a key to a certain unsigned long number (enum message) and a flag for what state the key should be in. Each loop I iterate through all the keys and if any of them is binded I check the flag and if that keystate is correct to the flag. If so I send away this unsigned long to the event manager so that the programmer has to handle it.

My first bind
InputManager()->BindKeyboardKey(DIK_ESCAPE, E_QUIT, IS_RELEASED);
Worked like a charm And admit it, the code has a nice look towards it ^^

Ah well, heading off to read some articles that got suggested here and read up on ActionMapping.. l8 guys

This topic is closed to new replies.

Advertisement