• Announcements

    • khawk

      Download the Game Design and Indie Game Marketing Freebook   07/19/17

      GameDev.net and CRC Press have teamed up to bring a free ebook of content curated from top titles published by CRC Press. The freebook, Practices of Game Design & Indie Game Marketing, includes chapters from The Art of Game Design: A Book of Lenses, A Practical Guide to Indie Game Marketing, and An Architectural Approach to Level Design. The GameDev.net FreeBook is relevant to game designers, developers, and those interested in learning more about the challenges in game development. We know game development can be a tough discipline and business, so we picked several chapters from CRC Press titles that we thought would be of interest to you, the GameDev.net audience, in your journey to design, develop, and market your next game. The free ebook is available through CRC Press by clicking here. The Curated Books The Art of Game Design: A Book of Lenses, Second Edition, by Jesse Schell Presents 100+ sets of questions, or different lenses, for viewing a game’s design, encompassing diverse fields such as psychology, architecture, music, film, software engineering, theme park design, mathematics, anthropology, and more. Written by one of the world's top game designers, this book describes the deepest and most fundamental principles of game design, demonstrating how tactics used in board, card, and athletic games also work in video games. It provides practical instruction on creating world-class games that will be played again and again. View it here. A Practical Guide to Indie Game Marketing, by Joel Dreskin Marketing is an essential but too frequently overlooked or minimized component of the release plan for indie games. A Practical Guide to Indie Game Marketing provides you with the tools needed to build visibility and sell your indie games. With special focus on those developers with small budgets and limited staff and resources, this book is packed with tangible recommendations and techniques that you can put to use immediately. As a seasoned professional of the indie game arena, author Joel Dreskin gives you insight into practical, real-world experiences of marketing numerous successful games and also provides stories of the failures. View it here. An Architectural Approach to Level Design This is one of the first books to integrate architectural and spatial design theory with the field of level design. The book presents architectural techniques and theories for level designers to use in their own work. It connects architecture and level design in different ways that address the practical elements of how designers construct space and the experiential elements of how and why humans interact with this space. Throughout the text, readers learn skills for spatial layout, evoking emotion through gamespaces, and creating better levels through architectural theory. View it here. Learn more and download the ebook by clicking here. Did you know? GameDev.net and CRC Press also recently teamed up to bring GDNet+ Members up to a 20% discount on all CRC Press books. Learn more about this and other benefits here.
Sign in to follow this  
Followers 0
mypel16000

Multiple instances of one class

15 posts in this topic

HI, I'm using C++ and SFML, I wanted to make a zombie game where 2 players start at the middle of a map and zombies come from the sides. I have already done my man's animation and screen scrolling, but I don't know how to do this. I am confident with the rest of c++ and sfml, but I would like someone to explain to me, in detail, how I could make multiple enemies, how to shoot multiple projectiles, make the enemies die when they are hit 3 times.....

Thank you
0

Share this post


Link to post
Share on other sites
mypel16000,

You should check out my [url="http://2dgamemaking.blogspot.com"]Old Blog[/url] (also linked in my sig). I detail the steps for making a top-down 2d game similar to what you are suggesting (player starts in map, enemies spawn from an "Enemy Spawn", bullets shooting everywhere).

(Here's the link to the entry on adding enemies to my game: [url="http://2dgamemaking.blogspot.com/2011/11/im-not-dead-enemies-added.html"]Click Here[/url])

In general, my Enemy Spawn's are considered an item, and I update it like this:

[code]
BOOL SmashPcItem::Update(void)
{

// Release Enemies into the level
if (mpItemDetails->Type == "EnemySpawn")
{
if (mu32NumReleaseLeft && (mu32LastRelease + mpItemDetails->u32ReleaseRate < timeGetTime()))
{
SmashPcEnemy *pEnemy;
mu32LastRelease = timeGetTime();
mu32NumReleaseLeft--;
// Create an enemy
pEnemy = new SmashPcEnemy(mGameData, mpApp, mpSpace,
mpBody->p, mpItemDetails->u32EnemyLevel);
// Check if this enemy should release something
mGameData.AddActiveEnemy(pEnemy);
}
}
return mbActive;
}
[/code]

Which basically says, if there are still enemies to release, and if it's time to release a new enemy, then create a new enemy, and add him to the list of active enemies. Here's what the enemies actually do (the full Enemy class here):
[code]
/******************************************************************************
*
* SmashPcEnemy() - Creates a player, and places him in the space
*
******************************************************************************/
SmashPcEnemy::SmashPcEnemy(SmashPcData &GameData,
sf::RenderWindow *pApp, cpSpace *pSpace,
cpVect Location, U32 u32Level) :
PhysicalObject(pApp, pSpace, "Gfx/blueenemy.bmp", "",
Location, PI/2.0f, 0.0f, TRUE),
mu32Health(20*u32Level),
mu32LastFire(timeGetTime()),
mu32LastMoveUpdate(0),
mGameData(GameData)
{
printf("Enemy created!\n");
// Set the Velocity limit to our fake movement
mpBody->v_limit = ENEMY_SPEED;
mpShape->collision_type = ENEMY_COL_TYPE;
mpShape->layers = ENEMY_PLAYER_LAYER;
mpShape->data = (void *)this;
// Create Collision handler here
cpSpaceAddCollisionHandler(mpSpace, ENEMY_COL_TYPE, BULLET_COL_TYPE, SmashPcEnemy::BulletCollision, NULL, NULL, NULL, NULL);
// Sound notifying a player has spawned
GameSound::Play("EnemySpawn");
}
/******************************************************************************
*
* ~SmashPcEnemy() - Removes a player
*
******************************************************************************/
SmashPcEnemy::~SmashPcEnemy()
{
}
/******************************************************************************
*
* Update() - Do enemy things
*
******************************************************************************/
void SmashPcEnemy::Update(cpBody *pPlayerBody)
{
U32 u32Time = timeGetTime();
// check if we need to update the movement
if (mu32LastMoveUpdate + ENEMY_UPDATE_MOVE < u32Time)
{
cpFloat Angle = atan2(pPlayerBody->p.y - mpBody->p.y,
pPlayerBody->p.x - mpBody->p.x);
// add randomization to angle
cpFloat RandomDegrees = (cpFloat)(((S32)rand() % 20) - 10);
Angle += (RandomDegrees*PI)/180.0f;
cpBodySetAngle(mpBody, Angle);
// Change force towards player
mForce = cpv(ENEMY_FORCE*cos(Angle), ENEMY_FORCE*sin(Angle));
//mpBody->f = cpv(ENEMY_FORCE*cos(Angle), ENEMY_FORCE*sin(Angle));
mu32LastMoveUpdate = u32Time;
}
mpBody->f = mForce;
if (mu32LastFire + ENEMY_REFIRE_TIME < u32Time)
{
SmashPcData::tBulletList BulletList;
mGameData.GetBulletList(BulletList);
SmashPcBullet *pBullet = new SmashPcBullet(mpApp, BulletList[0],
mpBody, mpSpace, FALSE);
mGameData.AddActiveBullet(pBullet);
mu32LastFire = u32Time;
}
}
/******************************************************************************
*
* NotifyHit() - Notify the enemy it has been hit by a bullet
*
******************************************************************************/
void SmashPcEnemy::NotifyHit(SmashPcBullet *pBullet)
{
if (mu32Health < pBullet->GetDamage())
{
// Enemy Dead
mu32Health = 0;
// Play dead sound
}
else
{
GameSound::Play("PlayerHit");
mu32Health -= pBullet->GetDamage();
}
pBullet->SetDead();
}
/******************************************************************************
*
* BulletCollision() - Callback for when Enemy hits a bullet
*
******************************************************************************/
int SmashPcEnemy::BulletCollision(cpArbiter *arb, struct cpSpace *space, void *data)
{
SmashPcBullet *pBullet;
SmashPcEnemy *pEnemy;
cpShape *pBulletShape, *pEnemyShape;
cpArbiterGetShapes(arb, &pEnemyShape, &pBulletShape);
pEnemy = reinterpret_cast<SmashPcEnemy*>(pEnemyShape->data);
pBullet = reinterpret_cast<SmashPcBullet*>(pBulletShape->data);
// We have the enemy that hit, and the bullet he hit
pEnemy->NotifyHit(pBullet);
return 0;
}
[/code]

I updated my enemies later on to make them a little smarter and to shoot better, but you get the picture. Edited by BeerNutts
2

Share this post


Link to post
Share on other sites
If I understand correctly, the original poster is asking how to handle an arbitrary number of objects such as enemies, provided he has the correct logic to handle one.

You can stick all the objects of that type in a single container, like std::vector<Enemy> allEnemies. Whenever you create a new enemy, you add it into that container like so: allEnemies.push_back(... your new enemy object ...). Whenever an enemy dies, you remove it from that container. To handle things like drawing all of them and having all of them take action, you just loop through all of the objects in the container on every game tick, like so:

[code]for(std::vector<Enemy>::size_type i = 0; i<allEnemies.size(); ++i) { allEnemies[i].draw(); }[/code]
or so:
[code]std::for_each(allEnemies.begin(), allEnemies.end(), [](&Enemy e){ e.draw(); });[/code]
or so:
[code]for(auto e : allEnemies) {e.draw();}[/code]
2

Share this post


Link to post
Share on other sites
Thank you two, I find your posts very helful. BeerNuts,I don't really understand some of your code, but I get the basics. Stroppy Katamari, yours really gives a good insight on what to do, but still, can you get me out of doubts:

- So to create enemies, should I just use my player class and add an AI function to it? How could I do this AI? After that should I just create, say, 10 enemies in an object array and loop through their functions just like the normal player(only that using AI instead of handle Input).
- And how could I make projectiles, you still havent talked about that.
0

Share this post


Link to post
Share on other sites
[quote name='mypel16000' timestamp='1351804232' post='4996308']- So to create enemies, should I just use my player class and add an AI function to it?[/quote]Where in the code you should create new enemies depends on the logic you intend the game to have. Is the player avatar in the game world actually creating enemies? Probably not.

For instance, if you want enemies to spawn randomly over time, just put a function in your main game loop which does that. Assuming you want an average of one new enemy every 3 seconds, and your game runs with 60 logic ticks a second, the function should spawn an enemy 1/(3*60) of the time and do nothing the rest of the time.

[quote]- And how could I make projectiles, you still havent talked about that.
[/quote]Who's shooting? If the player, then the player class' game logic should make new projectiles. If an enemy is shooting, the enemy class' game logic should make new projectiles. Put a tick() function on everything in the game and just call that function on every object once per game tick, just like the draw() function above. Enemies' tick() function will contain the enemies' AI, moving them around and doing stuff. Simple projectiles' tick() function will just keep moving the projectile in the direction it was fired, and perhaps count down to a time or distance where the projectile dissipates and removes itself from the game.

You can handle projectiles like you handle the enemies: place them in their own container when you create them, remove them from the container when they are supposed to die.
2

Share this post


Link to post
Share on other sites
For projectiles you may start simply. As stated before you may keep a vector or list of your projectiles and add projectile(s) when someone is shooting or remove projectile(s) when projectile has hit something or has timed out) objects as necessary.

Remember that your player / enemy doesn't own the projectiles. Keep all the projectiles in the one and same list.

Cheers!
0

Share this post


Link to post
Share on other sites
[quote name='Stroppy Katamari' timestamp='1351803398' post='4996306']
or so:
for(auto e : allEnemies) {e.draw();}
[/quote]

isn't this better?
[source lang="cpp"]for(const Enemy & e: allEnemies){e.draw();}[/source] Edited by lride
0

Share this post


Link to post
Share on other sites
Ok, thank you for all these ideas, but could someone explain to me how to make a vector containing items and how to add and delete elements from it. Also how could I make the projectiles functions. Give me some code please!
0

Share this post


Link to post
Share on other sites
[quote name='lride' timestamp='1351813884' post='4996364']
[quote name='Stroppy Katamari' timestamp='1351803398' post='4996306']
or so:
for(auto e : allEnemies) {e.draw();}
[/quote]

isn't this better?
[source lang="cpp"]for(const Enemy & e: allEnemies){e.draw();}[/source]
[/quote]Yes, I forgot the const and &.
0

Share this post


Link to post
Share on other sites
[quote name='mypel16000' timestamp='1351814364' post='4996370']
Ok, thank you for all these ideas, but could someone explain to me how to make a vector containing items and how to add and delete elements from it.
[/quote]http://www.cplusplus.com/reference/stl/vector/push_back/
http://www.cplusplus.com/reference/stl/vector/erase/
0

Share this post


Link to post
Share on other sites
Ok... that's not helping at all. Can you just show me how I would make my code. I have a person class containing all functions for a zombie, what i want to do is create a vector, make a certain amount of zombies(person class) inside them according to a rand() function, initialize them all and then during my main loop to update them. I thought of this code, but it just makes my player go really laggy and no zombies appear:

[source lang="cpp"] vector<Player> zombies (5);
Player *zombieO;

for (int n=0; n<5; n++)
{
int xR = rand() % 1000 + 1;
int yR = rand() % 800 + 1;
zombieO = new Player;
zombieO->initialize(xR, yR, 50);
zombieO->loadContent();
zombies.push_back(*zombieO);
}

while(Window.IsOpened())
{
sf::Event Event;
while(Window.GetEvent(Event))
{
if(Event.Type == sf::Event::Closed)
Window.Close();
}


vector<Player>::iterator it;
for ( it = zombies.begin(); it != zombies.end(); ++it ) {
zombieO->tick(player, Window);
zombieO->draw(Window);
}[/source]

Any help or other ideas? Also, can you also tell me how to do projectiles?
0

Share this post


Link to post
Share on other sites
[quote name='mypel16000' timestamp='1351854867' post='4996496']
Ok... that's not helping at all. Can you just show me how I would make my code. I have a person class containing all functions for a zombie, what i want to do is create a vector, make a certain amount of zombies(person class) inside them according to a rand() function, initialize them all and then during my main loop to update them. I thought of this code, but it just makes my player go really laggy and no zombies appear:

Any help or other ideas? Also, can you also tell me how to do projectiles?
[/quote]

mypel,

I've given you a link to look directly at my source code (you can download the full source from my Old Blog), and you've been given the webpage that explains vectors. You need to do some work yourself.

Your code looks OK, but there's still some issues. You don't need to declare how big a vector is, it is dynamic, so you can just push_back zombie's as you need them. ALso, don't create a new player pointer for the zombies just push an instance of them onto th vector, like this:
[code]
for (int i = 0; i < 5; ++i) {
int xR = rand() % 1000 + 1;
int yR = rand() % 800 + 1;
// Your player class should have the cxonstructor define the x, y, and (whatever 50 is), not a separate call to initialize
// the constructor can probably do whatever loadContent does too
Player zombie(xR, yR, 50);
zombies.push_back(zombie);
}
[/code]

Also, you're not looping through the zombies at all. Zombie0 is just the last zombie created in your loop. You need to be access the zombies form the vector. Again, the vector page will help, but here's what I would do:
[code]
for (int = 0; i < zombies.size(); ++i) {
zombies[i]->tick(player, Window);
zombies[i]->draw(Window);
}
[/code]

And projectiles aren't much different than adding a zombie as far as adding them to a vector, and looping through them all to process them. Edited by BeerNutts
1

Share this post


Link to post
Share on other sites
Thank you, but now its got worse, my program just crashes straight away, I don't know what to do... my code is probably full of bugs, Please, if someone could have a look over it and help me, that would be great! The files are here http://uploading.com/files/get/bd1494c6/moving%2Bman.rar

Please help, I have tried vectors with other games and they work, but there's a problem with this one.
0

Share this post


Link to post
Share on other sites
What IDE are you using? You need to learn to use the debugger, and find out what line is causing the crash? If you run it with the debugger, it will stop on the line that causes the crash.

Worse case, you throw some prints inside your code, see which line gets print and which doesn't. Then, work from there.

Honestly I think you need to step back from the game scene, and work on playing with objects in vectors, and looping through the objects and doing things to them in a simple program. Once you understand how it works, then you can move to the next thing.
0

Share this post


Link to post
Share on other sites
I have stepped back... I've done things like having a circle move around the screen and if you press a another one appears and if you press x it dissapears. I've also done an age, name and gender database using vectors...... that's not the problem anymore! I did what you did by commenting things out, and found the source of the problem, it is in the function tick(), and that always worked when I was working with 1 zombie...
0

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!


Register a new account

Sign in

Already have an account? Sign in here.


Sign In Now
Sign in to follow this  
Followers 0