Question about weapons

Started by
20 comments, last by Eej 21 years ago
Lately, i''ve been trying to create a space game (like star control to give you an idea, you know, top down) and i''ve kind of hit a snag with the actual firing and drawing of the bullets/missles/lasers. So how would i go about implementing the use of weapons into my game. One thing is that the weapons won''t dissappear if they go off screen, instead they have to wrap around to the other side [a la star control, again]. This part i got done just by moving the co-ordinates over, the main thing is the ability to fire repeatedly and dissappearing after a set amount of time. Also, we have to have the weapons start with the velocity of the ship and then continue on its path without being affected by the ship''s movement. Thanks,
Advertisement
a good idea is to use vectors for the acceleration/velocity/position.

if you are programming object-oriented style then create an independant bullet class...

class Bullet
{
Vector3f velocity;
Vector3f position;
int life; //life in frames or seconds

public:
Bullet(Vector3f position, velocity);

update/draw();

};

then when you fire, dynamically create one of these suckers then call it in your global update/draw routine,
where position+=velocity*timePassed;
if position>screenBoundary, then position= blahblah....
also life+=timePassed; and if life>1000 or whatever destroy the chump

Actually a good design would incorporate a base Object class that has member functions such as draw, update, and variables such as velocity, position...then all your specific object are just inherited from these. then you can create an ObjectManager singleton class that controls the creation/destruction and management of all the objects via polymorphism.

does this help???
You can''t name your function "update/draw"; that''s illegal in C/C++. You can only use numbers and letters and the underscore character. Your name can start with the under score or letter, but it cannot start with a number. Do you understand!
Keep coming back, because it's worth it, if you work it, so work it, you're worth it!
hmmm this was actualy something i was wondering myself, heres what i had so far...

//global things...
camera g_Camera //my camera, controls the view and such
projectile *bullet=NULL;

//projectile class
class projectile
{
public:
projectile();
projectile(vector3 starposition, vector3 startvelocity, vector3 startacceleration, unsigned int startlife);
void update();
unsigned int life;
private:
vector3 position;
vector3 velocity;
vector3 acceleration;

};

projectile:rojectile()
{
position.x=0;
position.y=0;
position.z=0;
velocity.x=0;
velocity.y=0;
velocity.z=0;
acceleration.x=0;
acceleration.y=0;
acceleration.z=0;
life=1000;
}

projectile:rojectile(vector3 startposition, vector3 startvelocity, vector3 startacceleration, unsigned int startlife)
{
position=startposition;
velocity=startvelocity;
acceleration=startacceleration;
life=startlife;
}

void projectile::update()
{
glBegin(GL_QUADS);

glColor3ub(255,0,0);
glVertex3f(position.x-1,position.y+1,position.z);
glVertex3f(position.x+1,position.y+1,position.z);
glVertex3f(position.x+1,position.y-1,position.z);
glVertex3f(position.x-1,position.y-1,position.z);

velocity=velocity+acceleration;
position=position+velocity;

life--;
glEnd();
}


//WinProc, this is where i check to see if Z has been pressed to fire the projectile

LRESULT CALLBACK WinProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
LONG lRet=0;
PAINTSTRUCT ps;

switch (uMsg)
{
case WM_SIZE: if (!g_bFullScreen)
{
SizeOpenGLScreen(LOWORD(lParam),HIWORD(lParam));
GetClientRect(hWnd,&g_rRect);
}
break;
case WM_PAINT: BeginPaint(hWnd,&ps);
EndPaint(hWnd,&ps);
break;
case WM_KEYDOWN: switch (wParam)
{
case VK_ESCAPE: PostQuitMessage(0);
break;

case ''Z'': if (bullet==NULL)
{
vector3 sposition;
sposition.x=g_Camera.view.x-g_Camera.position.x;
sposition.y=g_Camera.view.y-g_Camera.position.y;
sposition.z=g_Camera.view.z-g_Camera.position.z;
vector3 svelocity;
svelocity.x=0;
svelocity.y=0;
svelocity.z=0.1f;
vector3 sacceleration;
sacceleration.x=0;
sacceleration.y=0;
sacceleration.z=0.0;
bullet=new projectile(sposition,svelocity,sacceleration,100);
}
break;

}
break;
case WM_CLOSE: PostQuitMessage(0);
break;
default: lRet=DefWindowProc(hWnd,uMsg,wParam,lParam);
break;
}

return lRet;
}

//function that does the drawing for the entire environment
void RenderScene()
{
glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT);
glLoadIdentity();

gluLookAt(g_Camera.position.x,g_Camera.position.y,g_Camera.position.z,g_Camera.view.x,g_Camera.view.y,g_Camera.view.z,g_Camera.upvector.x,g_Camera.upvector.y,g_Camera.upvector.z);

//draw scene here
// wireframecube(1,0,0,0,255,0,0);
// wireframecube(2,0,0,0,0,255,0);
// wireframecube(3,0,0,0,0,0,255);

// trianglematrix(6,2,0,0,0);

if (bullet!=NULL)
{
bullet->update();
if (bullet->life<=0)
{
delete bullet;
bullet=NULL;
}
}



SwapBuffers(g_hDC);
}

it sorta works, it doesnt go in the direction i hoped, but hey, its a start at making projectiles =P

Bungo!
Bungo!
lol changed it so under the update function this is what is used...

glVertex3f(position.x-0.1f,position.y+0.1f,position.z);
glVertex3f(position.x+0.1f,position.y+0.1f,position.z);
glVertex3f(position.x+0.1f,position.y-0.1f,position.z);
glVertex3f(position.x-0.1f,position.y-0.1f,position.z);

makes the square smaller, which actualy seems to make a difference

now to figure out how to make it go forward lol
and how to make it stop once it goes out too far =P

Bungo!
Bungo!
oh, and while im thinkin about it, how would i go about making it so i didnt necessarily have to have a global pointer, or even a global array (for multiple projectiles). i cant really see a way to do it, cause itd have to be created in the RenderScene() function, and that function is called by another function that uses an infinate loop (to continualy draw the scene). so im at a loss as to how else it could be done, but i know there has got to be a way, cause if there isnt then itd get very messy when you had for example, multiple characters firing multiple shots =/ bah!

Bungo!
Bungo!
heres what i reckon u do:

1. for a start don't rely on the camera to get coords, each OBJECT has there own positions, which when drawn are then affected by the camera's position simply by using a glTranslate function or whatever.
2. get rid of acceleration for bullets, they should have a const velocity which is velocity of ship+some number.
3. use an Object Manager singleton class to create ALL objects. if you don't know what a singleton class is then have a read up of gamedev articles. basically it means that there is only ever one instance of a class made at one time. enabling you to pass a reference of it to any other files/classes and they can access the information within them (bad explanation!)
4. either create a linked list structure class, or just use STL's vector, or better yet- map, for the storage of all your objects.

*i was just thinking, if ur not comfortable with polymorphism, then u could create manager classes for each object type...like ShipManager, BulletManager, AsteroidManager...etc


    //basicallyclass BulletManager{//input singleton stuff ....//has one vector to store all objects...vector<Bullet>bulletList;vector<Bullet>iterator it;//container iteratorpublic://blah blah blahvoid addBullet();void update();};void addBullet(){ Bullet newbullet; it.push(newbullet);}void ObjectManager::update(){ for(it=objectList.begin(); it!=objectList.end(); it++) {  it->update(); //calls the individual Objects update function (syntax maybe wrong) }}/////BulletManager& bulletManager = BulletManager::getHandle();//singleton stuff///keyboard handler////case 'Z': {vector3 sposition=ship.getPosition();vector3 svelocity=ship.getVelocity();bulletManager.addbullet(sposition, svelocity+bulletconstant);break;}    




i have probably confused you even more, but this is the general track u should follow for a nice and clean game structure...

and thinking about it, using a queue for the bullets would actually be a lot quicker and easier to implement, as all the bullets have the same life span

[edited by - kuladus on March 25, 2003 5:31:17 AM]
i thought about using vectors (along with a queue of some sort), i dont know what a singleton is, but ive at least heard of them, ill look into them and see if that helps in the slightest

Bungo!
Bungo!
i took your idea on singletons and tried to impliment it, most of it seems to work, but one function (which you wrote)...

void projectilemanager::update()
{
for(it=projectileslist.begin();it!=projectileslist.end();it++)
{
it->update();
}
}

i think i see what that function does, it sets the iterator vector to the begining of the projectile vector. then it goes through each one in the list, then updates it. seems ok, except it gives me the following errors:

--------------------Configuration: Camera2 - Win32 Debug--------------------
Compiling...
Main.cpp
c:\program files\microsoft visual studio\my projects\miscellaneous\camera part 2\main.cpp(177) : error C2660: ''addprojectile'' : function does not take 3 parameters
projectilemanager.cpp
c:\program files\microsoft visual studio\my projects\miscellaneous\camera part 2\projectilemanager.cpp(35) : error C2679: binary ''='' : no operator defined which takes a right-hand operand of type ''class projectile *'' (or there is no acceptable conve
rsion)
c:\program files\microsoft visual studio\my projects\miscellaneous\camera part 2\projectilemanager.cpp(35) : error C2678: binary ''!='' : no operator defined which takes a left-hand operand of type ''class std::vectortor >'' (or there is no acceptable conversion)
c:\program files\microsoft visual studio\my projects\miscellaneous\camera part 2\projectilemanager.cpp(35) : error C2676: binary ''++'' : ''class std::vector >'' does not define this operator or a
conversion to a type acceptable to the predefined operator
c:\program files\microsoft visual studio\my projects\miscellaneous\camera part 2\projectilemanager.cpp(37) : error C2819: type ''std::vector >'' does not have an overloaded member ''operator ->''
c:\program files\microsoft visual studio\my projects\miscellaneous\camera part 2\projectilemanager.cpp(37) : error C2227: left of ''->update'' must point to class/struct/union
Error executing cl.exe.

Camera2.exe - 6 error(s), 0 warning(s)

seems to have to do with the STL vector lacking those overloaded operators or something... im not totaly sure how to fix this cause i am only just understanding the whole process here...

here is the class i have going so far (the projectile manager singleton)

//projectilemanager.h
#ifndef _projectile_manager_h
#define _projectile_manager_h

#include <vector>

class projectilemanager
{
public:
~projectilemanager();
static projectilemanager* create();
void addprojectile(vector3 sposition, vector3 svelocity, vector3 sacceleration, int slife);
void update();
private:
projectilemanager();
static bool flag;
static projectilemanager *instance;
std::vector projectileslist;
std::vector it;
};

#endif


//projectilemanager.cpp
#include "main.h"

bool projectilemanager::flag=false;
projectilemanager* projectilemanager::instance=NULL;

projectilemanager:rojectilemanager()
{

}

projectilemanager::~projectilemanager()
{
flag=false;
}

projectilemanager* projectilemanager::create()
{
if (!flag)
{
flag=true;
instance=new projectilemanager;
}

return instance;
}

void projectilemanager::addprojectile(vector3 sposition, vector3 svelocity, vector3 sacceleration, int slife)
{
projectile newprojectile(sposition,svelocity,sacceleration,slife);
it.push_back(newprojectile);
}

void projectilemanager::update()
{
for(it=projectileslist.begin();it!=projectileslist.end();it++)
{
it->update();
}
}


//inside main.cpp (the file with all the global functions and fun stuff
#include "main.h" //where #include "projectilemanager.h" can be found (just so you know)

projectilemanager *projectiles=projectilemanager::create();

//under WinProc
case ''Z'': vector3 sposition;
sposition.x=g_Camera.view.x-g_Camera.position.x;
sposition.y=g_Camera.view.y-g_Camera.position.y;
sposition.z=g_Camera.view.z-g_Camera.position.z;
vector3 svelocity;
svelocity.x=0.0f;
svelocity.y=0.0f;
svelocity.z=-0.1f;
vector3 sacceleration;
sacceleration.x=0.0f;
sacceleration.y=0.0f;
sacceleration.z=0.0f;
projectiles->addprojectile(sposition,svelocity,sacceleration,100);
break;

//under the RenderScene() function, the function that updates continualy draws everything

projectiles->update();


i think thats all the relevant code =P

Bungo!
Bungo!
i kinda figured it was worth a shot...

for (int x=0;x {
projectileslist[x].update();
}

didnt work =/

Bungo!
Bungo!

This topic is closed to new replies.

Advertisement