🎉 Celebrating 25 Years of GameDev.net! 🎉

Not many can claim 25 years on the Internet! Join us in celebrating this milestone. Learn more about our history, and thank you for being a part of our community!

isometric game tiling

Started by
46 comments, last by pbivens67 8 months, 3 weeks ago

pbivens67 said:

so should I use vectors or arrays?

Will your tile maps ever change dimensions? In other words, will one level have a 32x32 map (for example) and the next 64x64? If the answer is no, use an array. If the answer is yes, use a vector.

[edit] Generally, vectors are considered preferable to most other array methods and can be accessed just like an array. It would probably be better to learn and use vectors.

No, I am not a professional programmer. I'm just a hobbyist having fun...

Advertisement

how do I use a vector to populate a map with sprites?

A vector is just a container. All it would do is store the sprite class data. What you do with it after is up to you.

class Sprite{
	// Sprite data stuff and junk.
};

void main(void)
{
	Sprite					sprite;
	std::vector<Sprite>		sprites;

	sprite.sprite_stuff = stuff_and_junk;
	sprites.push_back(sprite);

	//Do stuff with sprites...
}

No, I am not a professional programmer. I'm just a hobbyist having fun...

is there a way to store over 200 sprites in a highly efficient manner?

pbivens67 said:

is there a way to store over 200 sprites in a highly efficient manner?

Use a vector. 200 sprites is a tiny amount on modern systems. Most particle systems use thousands of screen aligned sprites.

No, I am not a professional programmer. I'm just a hobbyist having fun...

While there might be performance problems in how you actually draw the sprites, the 200 sprites themselves are not going to be a performance issue.

A modern computer has 4+ cores, each core can handle many billion instructions per second. In ideal conditions each processor can ingest over 20 billion instructions per second. The computer might have 4 of them, 8 of them, even 64 of them, each one pulling in billions of instructions.

You can do things terribly and consume many million cycles to draw each one and still have time to spare.

Is there a way to draw sprites using vectors not one at a time but several at a time.

pbivens67 said:

Is there a way to draw sprites using vectors not one at a time but several at a time.

You're going to be rendering geometry on the GPU. Don't just store the position of the sprite in the data structure; store the associated geometry. When you render, you send that geometry to the GPU, either with OpenGL, GL ES, Vulkan or DirectX. There is actually better ways of doing it through shaders, where you send all of the geometry up front and move the sprites directly on the GPU through shaders. Regardless, what you're talking about are two different things; storing data and rendering sprites. The two are vastly separate topics.

Also, remember the mantra: "Make games, not engines." There are several free game engines that will easily work with isometric tiles. Check out Godot.

No, I am not a professional programmer. I'm just a hobbyist having fun...

Said differently:

Yes, there are ways to do it. But no, you are not yet in a position to implement them.

pbivens67 said:

Is there a way to draw sprites using vectors not one at a time but several at a time.

Do it like you did all the time. It will be fast enough for your needs, even if you have hundreds of map tiles and sprites.

But previously you have drawn only one sprite. Now you need to loop over all sprites in your vector, something like that:

for (int i=0; i<sprites.size(); i++) // loop over all sprites
{
	Sprite &sprite = sprites[i]; // our current sprite to render
	
	// todo: activate the texture of the current sprite, but i have forgotten how OpenGL calls are named.
	
	// now we draw the current sprite
	glBegin(GL_QUADS);
	glVertex3dv (sprite.vertices[0].pos); glTexcoord2dv (sprite.vertices[0].uv); // may be all wrong - i can't rmember OpenGL
	glVertex3dv (sprite.vertices[1].pos); glTexcoord2dv (sprite.vertices[1].uv);
	glVertex3dv (sprite.vertices[2].pos); glTexcoord2dv (sprite.vertices[2].uv);
	glVertex3dv (sprite.vertices[3].pos); glTexcoord2dv (sprite.vertices[3].uv);
	glEnd();
}
	

This assumes your sprite data structure looks somehow like that:

struct Vertex // let's use another data structure just for vertices to draw from OpenGL
{
	float pos[3]; // or float posX, posY, posZ;
	float uv[2];
};

struct Sprite
{
	// some random variables you may have per sprite for gameplay, eventually
	float centerX, centerY;
	int type, state, health, andWhateverElse;
	
	// the data for rendering 
	Vertex vertices[4]; // using the Vertex data structure as declared above, and an array to have 4 vertices
};

That's just an example. Make your sprite in any way you imagine.
You can always change your mind about it and change it later, depending on what you need for a current game.
It's arguable if we want gameplay and render data in the same data structure, but for now it does not matter. It only matters you start using those data structures at all. Only after that you may notice various design flaws such as putting too much stuff into a single data structure.

Be creative and do trial and error.
There is no one and only way for a ‘correct’ Sprite struct/class we could tell you. (At least not i, since i never made something like a 2D game engine.)
Begin with a single sprite - you have to setup all it's vertices manually to draw it.
Then add a second at another position.
Eventually you write some code to set the positions of 5 x 3 sprites so they form a grid, so you can render many sprites, just to see that it works.
Experiment and have fun.

Some notes about efficient rendering:
There are better ways. For example, we could sort the sprites by texture, so we reduce the number of texture switches.
glBegin()/glEnd() also is a deprecated way to render anything. It's slow. We should use vertex arrays objects instead (if that was the name). Etc.
But nothing of this matters to you. glBegin()/glEnd() is most easy to use, and it's good enough. You better learn about performance with your own code, instead caring about using blackboxed gfx APIs efficiently.

I have chosen 3D coordinates over 2D, although we have only a 2D game in mind.
But the z coordinate is useful. You can use it to decide which sprite is drawn in front of another, but ofc. you need to enable depth test.
But you can care about this later.

frob said:
Yes, there are ways to do it. But no, you are not yet in a position to implement them.

He is ready. He has rendered sprites before. He only needs to make the jump from creating just one sprite, together with rendering code specific to this single sprite, towards using data structures to handle multiple objects, all processed with the same code.
That's the concept he has missed all the time, i think.

This topic is closed to new replies.

Advertisement