TorquX equivalent of the 'update' method in plain old XNA?
by Mario Roberti · in Torque X 2D · 06/22/2007 (6:26 pm) · 18 replies
Apologies if I double posted. My stupid browser just bailed on me. :)
I'm looking to be able to check for gamestates in my game and display the appropriate stuff accordingly. Think of Galciv2 for instance. You have your big old starmap that you can scroll around (did this in TorqueX already)....but now I want to be able to switch views when I click on my stars over to a planet view (or hell, ANY other view).
In my XNA version, I simply check the gamestate in the:
I tried posting in another thread asking about the similar subject:
http://www.garagegames.com/mg/forums/result.thread.php?qt=62074
but there was nary a response! All I'm hoping for is the finger.
Pointing me in the right direction.
Best,
Mario
I'm looking to be able to check for gamestates in my game and display the appropriate stuff accordingly. Think of Galciv2 for instance. You have your big old starmap that you can scroll around (did this in TorqueX already)....but now I want to be able to switch views when I click on my stars over to a planet view (or hell, ANY other view).
In my XNA version, I simply check the gamestate in the:
protected override void Update(GameTime gameTime)
{
// my code here checks to see what gamestate I'm in, strategic map, solarsystem, planet map, research, etc.
// Then call the appropriate method
if(gameMode=="Starmap")
{
displayStarmap();
}
if(gameMode=="Solarsystem")
{
displaySolarsystem(solarSystemName);
}
etc. etc.
}I tried posting in another thread asking about the similar subject:
http://www.garagegames.com/mg/forums/result.thread.php?qt=62074
but there was nary a response! All I'm hoping for is the finger.
Pointing me in the right direction.
Best,
Mario
About the author
#2
But that still leaves me without a way to check to see what gamestate I'd be in to actually direct the camera to the appropriate spot to display? I guess I'm used to a constantly called method that checks to see if any changes have been made to the gamestate, i.e.
THATS the part I'm totally lost on. Since TorqueX takes care of so much for me behind the scenes, I'm kinda lost. :) All the events I've used so far are kinda built in to the components, but there's no one, grand sort of master controller sort of thing that I can have keep an eye on everything.
06/22/2007 (8:18 pm)
Ahh I see. So kinda treat the single scenegraph like a giant drafting table and lay all my stuff out and about and only concentrate on it when it's needed? Damn! That's a pretty nifty idea. I never thought of that. That solves that problem.But that still leaves me without a way to check to see what gamestate I'd be in to actually direct the camera to the appropriate spot to display? I guess I'm used to a constantly called method that checks to see if any changes have been made to the gamestate, i.e.
if(onStrategicMap)
{
move ships
check distance between ships on the strategic map
if(distance of any ships to other ships is<100km)
{
call method that will point the camera
to my portion of the scenegraph and engage combat routine
}
}THATS the part I'm totally lost on. Since TorqueX takes care of so much for me behind the scenes, I'm kinda lost. :) All the events I've used so far are kinda built in to the components, but there's no one, grand sort of master controller sort of thing that I can have keep an eye on everything.
#3
but again, maybe i'm not following you.
A less "simplistic" solutino would be to turn this into a stateMachine, which is what i do for my project. (I use torquex as the graphics layer, with everythign else being done in my custom code)
hope that helps!
-Jason
06/22/2007 (8:41 pm)
I'm actually not really sure what the problem is you are seeing, it sounds like the only thing missing from your logic is something like:if(stateChanged)
{
if(onStrategicMap)
{
LoadStrategicMap();
}else{
LoadStarMap();
}
}
if(onStrategicMap)
{
UpdateStrategicMap();
}else{
UpdateStarMap();
}but again, maybe i'm not following you.
A less "simplistic" solutino would be to turn this into a stateMachine, which is what i do for my project. (I use torquex as the graphics layer, with everythign else being done in my custom code)
hope that helps!
-Jason
#4
Does that do what you want?
Be careful, though, that you're not trying to centralize some things which might be better done in a distributed manner. For example, it might make more sense for each ship, as it reaches various waypoints on it's path, to query a central state machine and ask "should I keep moving", rather than iterating through every ship in existence every tick and deciding whether it should move or not. Figuring out the best organization for any given game can sometimes be tricky.
06/22/2007 (9:05 pm)
@Mario - If you need something to happen every tick (which isn't exactly the same as every frame, but is probably a better choice for things like control logic) you can create an object that can be registered for a tick callback:using System;
using System.Collections.Generic;
using System.Text;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Input;
using GarageGames.Torque.Core;
using GarageGames.Torque.T2D;
using GarageGames.Torque.Sim;
using GarageGames.Torque.Platform;
namespace StarterGame
{
class GameController : TorqueObject, ITickObject
{
#region Constructors
#endregion
#region Public properties, operators, constants, and enums
public int Mode
{
get { return _mode; }
set { _mode = value; }
}
#endregion
#region Public Methods
public void InterpolateTick(float k)
{
}
public void ProcessTick(Move move, float elapsed)
{
if (_mode == 0)
{
// do mode 0 stuff
}
else
{
// do mode 1 stuff
}
}
#endregion
#region Private, protected, internal methods
#endregion
#region Private, protected, internal fields
int _mode = 0;
#endregion
}
}And you would register the callback like this:GameController ControlEverything = new GameController(); ProcessList.Instance.AddTickCallback(ControlEverything);
Does that do what you want?
Be careful, though, that you're not trying to centralize some things which might be better done in a distributed manner. For example, it might make more sense for each ship, as it reaches various waypoints on it's path, to query a central state machine and ask "should I keep moving", rather than iterating through every ship in existence every tick and deciding whether it should move or not. Figuring out the best organization for any given game can sometimes be tricky.
#5
@Dan: I'll try that code example, I appreciate it!
@Jason: I got the code part you show, but I just don't know WHERE to put that? :) That's what's kinda maddening coming over from XNA to Torque; I don't have that main little "update" method that XNA does. Different, to be sure! Would you be able to share an example of how you got yours working with the stateMachine approach? You can always email me, I'd appreciate any help!
Well that does it. I'm buying TorqueX! :) Thanks for showing me it's possible to make more than arcade twitch style shootemups (not that there's anything wrong with those!).
-Mario
06/22/2007 (9:33 pm)
Hey guys, thanks for your info! @Dan: I'll try that code example, I appreciate it!
@Jason: I got the code part you show, but I just don't know WHERE to put that? :) That's what's kinda maddening coming over from XNA to Torque; I don't have that main little "update" method that XNA does. Different, to be sure! Would you be able to share an example of how you got yours working with the stateMachine approach? You can always email me, I'd appreciate any help!
Well that does it. I'm buying TorqueX! :) Thanks for showing me it's possible to make more than arcade twitch style shootemups (not that there's anything wrong with those!).
-Mario
#6
All you need to do, is, from the Game class (which if you load one of the starter games, is the one that "Main" creates, and the one that inherits from TorqueGame)
from your Game class, override the .Update(Gametime time) method. Same thing if you want something to occur each tick (which is not recomended), you can override the Draw(Gametime time) method.
hope that helps.
06/29/2007 (3:55 am)
@Mario, well, torque does use that "update" method that torque does, it overrides it (and you are using it too, in the .... oh wait, your first post says "in my xna code i do this".....All you need to do, is, from the Game class (which if you load one of the starter games, is the one that "Main" creates, and the one that inherits from TorqueGame)
from your Game class, override the .Update(Gametime time) method. Same thing if you want something to occur each tick (which is not recomended), you can override the Draw(Gametime time) method.
hope that helps.
#7
string/enum _gamestate;
public string/enum GameState
{
get
{
return _gamestate;
}
set{
_gamestate = value;
switch(_gamestate)
{
case....
}
}
}
then you wont need to check for changes to the gamestate, the gamestate's change will directly cause the visible change.
at least thats what I think...
06/29/2007 (4:21 am)
You could set the gamestate as a property of something, and then you wont need to check it, only do things when it changes, like:string/enum _gamestate;
public string/enum GameState
{
get
{
return _gamestate;
}
set{
_gamestate = value;
switch(_gamestate)
{
case....
}
}
}
then you wont need to check for changes to the gamestate, the gamestate's change will directly cause the visible change.
at least thats what I think...
#8
You all seem to agree that checking every tick for updates is NOT the way to go. THATS the part I'm having a tough time getting my head around. I've never done any programming any other way. I'm doing some reading up on state machine stuff. No idea how to implement 'em, but I'll be pestering you guys for help I'm sure.
Again, if anyone has some demo/pseudo code on state machine style stuff with TorqueX, I'd love to take a gander at it!
Thanks guys!
06/29/2007 (10:10 am)
Thanks again for all the recommendations, I really appreciate 'em!You all seem to agree that checking every tick for updates is NOT the way to go. THATS the part I'm having a tough time getting my head around. I've never done any programming any other way. I'm doing some reading up on state machine stuff. No idea how to implement 'em, but I'll be pestering you guys for help I'm sure.
Again, if anyone has some demo/pseudo code on state machine style stuff with TorqueX, I'd love to take a gander at it!
Thanks guys!
#9
You actually defined a state machine design in your original post, but your implementation was tick based instead of event based, which is what I personally think people are trying to point out.
It's a design perspective really--do I want to check every single tick (could be dozens or hundreds of times per second) to see what I should do, or do I want to structure what I should do so that when a state changes, it only calls/updates things that are appropriate for that state?
To try to break it down further using your example, we have two perspectives:
(psuedocode follows)
vs
06/29/2007 (10:25 am)
At it's root, a state machine is literally a couple of variables that store current game state (like you mention), and a big old switch statement that determines what to do based on those variables.You actually defined a state machine design in your original post, but your implementation was tick based instead of event based, which is what I personally think people are trying to point out.
It's a design perspective really--do I want to check every single tick (could be dozens or hundreds of times per second) to see what I should do, or do I want to structure what I should do so that when a state changes, it only calls/updates things that are appropriate for that state?
To try to break it down further using your example, we have two perspectives:
(psuedocode follows)
for every tick do
{
call every object in simulation
do something based on current state, even if it didn't change
{vs
on state change (oldState, newState)
{
call objects that need to know about [b]oldState[/b] ending
call objects that need to know about [b]newState[/b] starting
}
#10
-Mario
06/29/2007 (10:33 am)
Hey cool! OK, I get that the second version is far more efficient as it only executes the code on a statechange. Now if I can elevate my request from pseudo code to actual code, I can get to it. Plus, I'm reading up on the whole state machine stuff now on the web. If I can get a basic example of it implemented in TorqueX I'd be on my way.....till the next set of questions. :)-Mario
#11
"@Mario - Maybe it would be easier to help you if you could explain what you\\\'re trying to do in terms of what effect you\\\'re trying to achieve, rather than how you\\\'d approach it in some other tool.
The specific example you have is switching between the galaxy map and the solar system map. How are you deciding to go from one to the other? Some kind of user-clickable button? A game state transition from \\\"strategic\\\" to \\\"tactical\\\"? What you should do is figure out where and how that transition happens, and make the camera change part of that process. Rather than check every cycle, just do the big changes on transitions."
Yeah you hit the nail on the head. I'd click on a button to switch views, and a "next" button to calculate the turn process, i.e. ships move to their destinations on the strategic map, planets produce ships and research behind the scenes(no graphics), and a million other things (but for brevity's sake, just those two would be fine. They would give me exactly what I'd need).
What button would I want to click on? Well, I haven't researched the GUI stuff too much, so a simple keyclick would be fine for me. Again, I have the examples laid out from the TorqueX documentation, but it seems all input is a component, attached to an actual OBJECT from within the TXB. I have no clue how to implement an abstract object that floats around out there and waits for the state change to occur.
So short version:
I start off in my strategic mapmode
I want to click on a button on the controller (or keyboard) and change the gamestate from strategic to solarsystemview
Solarsystem view will place the camera a few hundred units away so we can overlook another spot on the map and do some neato combat (This is along the lines of your first suggestion to me since there's only one scenegraph right now) All of the graphics would be created on the fly, not setup in Torquex. I mean, there can be some dummy objects for now.
To show I'm not a total schmuck, I have a basic project skeleton already in place:
interstellarwarfare.com/devjournal/MarioStarter.zip
That loads some images and animations from TXB, I use custom code to make different starsystems, I have my ship controllable by the left stick on the 360 controller, and you can fly around and the camera follows. Um, the camera rotation is....yeah I need to work on that. But I got the basics! I just need that little push to get this 'event based' or 'state machine' stuff working in my program (and BRAIN!).
Thanks again all, you've given me quite a bit of feedback and I appreciate it!
06/29/2007 (11:20 am)
Hey Dan! You're right, I'm being kinda vague. I apologize! (Not sure why your post isn't showing up in the thread, so I'll paste it below)"@Mario - Maybe it would be easier to help you if you could explain what you\\\'re trying to do in terms of what effect you\\\'re trying to achieve, rather than how you\\\'d approach it in some other tool.
The specific example you have is switching between the galaxy map and the solar system map. How are you deciding to go from one to the other? Some kind of user-clickable button? A game state transition from \\\"strategic\\\" to \\\"tactical\\\"? What you should do is figure out where and how that transition happens, and make the camera change part of that process. Rather than check every cycle, just do the big changes on transitions."
Yeah you hit the nail on the head. I'd click on a button to switch views, and a "next" button to calculate the turn process, i.e. ships move to their destinations on the strategic map, planets produce ships and research behind the scenes(no graphics), and a million other things (but for brevity's sake, just those two would be fine. They would give me exactly what I'd need).
What button would I want to click on? Well, I haven't researched the GUI stuff too much, so a simple keyclick would be fine for me. Again, I have the examples laid out from the TorqueX documentation, but it seems all input is a component, attached to an actual OBJECT from within the TXB. I have no clue how to implement an abstract object that floats around out there and waits for the state change to occur.
So short version:
I start off in my strategic mapmode
I want to click on a button on the controller (or keyboard) and change the gamestate from strategic to solarsystemview
Solarsystem view will place the camera a few hundred units away so we can overlook another spot on the map and do some neato combat (This is along the lines of your first suggestion to me since there's only one scenegraph right now) All of the graphics would be created on the fly, not setup in Torquex. I mean, there can be some dummy objects for now.
To show I'm not a total schmuck, I have a basic project skeleton already in place:
interstellarwarfare.com/devjournal/MarioStarter.zip
That loads some images and animations from TXB, I use custom code to make different starsystems, I have my ship controllable by the left stick on the 360 controller, and you can fly around and the camera follows. Um, the camera rotation is....yeah I need to work on that. But I got the basics! I just need that little push to get this 'event based' or 'state machine' stuff working in my program (and BRAIN!).
Thanks again all, you've given me quite a bit of feedback and I appreciate it!
#12
In Torque X, anything that derives from TorqueObject can have components and is a valid choice for a ControlObject in the PlayerManager (we like to have input connected to objects to ease any future networking support that gets built into the engine). So there are a lot of things you can do. You might use the camera object as your control object (although it's a bit inconvenient to attach components to it since you can't do it in TXB). If you have a "pointer" of some kind that you use to select units, that might be a good place to stick your input.
So, assuming you've got a pointer object that has a component which is taking care of the bulk of your high-level game logic, you could do something like (pseudocode):
06/29/2007 (11:51 am)
@Mario - The reason my post isn't showing up was because I started writing it before Stephen's post, but after it was up it seemed to be covering the same territory as his, so I deleted it. :)In Torque X, anything that derives from TorqueObject can have components and is a valid choice for a ControlObject in the PlayerManager (we like to have input connected to objects to ease any future networking support that gets built into the engine). So there are a lot of things you can do. You might use the camera object as your control object (although it's a bit inconvenient to attach components to it since you can't do it in TXB). If you have a "pointer" of some kind that you use to select units, that might be a good place to stick your input.
So, assuming you've got a pointer object that has a component which is taking care of the bulk of your high-level game logic, you could do something like (pseudocode):
GoToGameState(newState)
{
oldState = state;
state = newState;
if ((newState == "system") && (oldState == "strategic"))
{
// move camera
}
}Then, you can set it up so that GoToGameState gets called when you click on a button, or maybe when the AI wants to initiate an attack, etc.
#13
"So, assuming you've got a pointer object that has a component which is taking care of the bulk of your high-level game logic...."
THIS is where I am lost. Where do I set this magical component up? HOW do I set this magical component up? HOW do I register it to the game to be checked for the even change?
06/29/2007 (12:00 pm)
THIS:"So, assuming you've got a pointer object that has a component which is taking care of the bulk of your high-level game logic...."
THIS is where I am lost. Where do I set this magical component up? HOW do I set this magical component up? HOW do I register it to the game to be checked for the even change?
#14
06/29/2007 (12:12 pm)
@Mario - Do you have any objects that will be present in every mode of your game? Maybe a "selector" sprite that shows you what you're clicking on? If so, that's the easiest place to start, since it's easy to stick components on them in TXB.
#15
06/29/2007 (12:17 pm)
I'd love to have a selector sprite controlled by the mouse. I haven't looked into that yet. Can I get back to you once I have a mouse selector sprite up and going?
#16
06/29/2007 (1:35 pm)
Well looks like mouse control is a whole 'nother kettle of fish judging by the posts. I have to go to work now, who knows? Maybe I can get a mouse controlled sprite going sometime and get back to you. Thanks for all the advice.
#17
Hugs,
Mario
07/10/2007 (7:58 pm)
So I'd love to have one of my sprites hooked up to the mouse, so hopefully I could register some events to that. Anyone have any ideas to point me in the right direction? I've been failing miserably. I'd even love to just start with a fresh project and take it from there just to get this whole mouse-thing going.Hugs,
Mario
#18
07/11/2007 (9:36 am)
@Mario - Supporting gamepad control was higher priority for us than mouse control due to the cross-platform functionality you can get with Creator's Club, so our mouse support isn't super great yet. However, here is a function that will get you the mouse position in world coordinates:public static Vector2 GetMousePosition()
{
MouseState state = Mouse.GetState();
T2DSceneCamera cam = T2DSceneGraph.Instance.Camera as T2DSceneCamera;
Vector2 mousePosition = new Vector2();
mousePosition.X = (((float)state.X / GUICanvas.Instance.Size.X) - 0.5f) * (cam.Extent.X) + cam.CenterPosition.X;
mousePosition.Y = (((float)state.Y / GUICanvas.Instance.Size.Y) - 0.5f) * (cam.Extent.Y) + cam.CenterPosition.Y;
return mousePosition;
}This isn't very robust code (for instance, it won't work right if your scene window doesn't cover the entire window area, and doesn't take into account any other GUI elements you might have) but it might help you make some progress.
Torque Owner Dan Maruschak