Drawing Sprites with SFML & C++ – Game Dev Tutorial

You can access the full course here: Discover SFML for C++ Game Development

Drawing Sprites

We’ve seen how to draw a basic shape but realistically, most of our games will use more than shapes. We will want to place graphics, icons, and other images into our games and we do so via Sprites. Setting up a Sprite is generally done in two steps with SFML: first, we load in a texture, then we create a sprite and pass in the texture. Once we have the sprite set up, we can set attributes such as the size and position and then display it by drawing it into the window during the run loop.

In our project, we should create a folder called assets that contains any assets needed in our game. We only have 4 so there’s no need to further divide the assets folder. Copy the “enemy.png” and “background.png” images, the “damage.ogg” audio file, and the “Arial.ttf” font files from your provided files and paste them into the assets folder. We will only work with the Enemy.png image for now. To create a texture, we first create a texture variable and then call the loadFromFile() function, passing in the path to the file as a string. It returns true if successful and false otherwise so we should perform a boolean test to see if the load was successful. In our main function, write this code after the code to create the window and before the run loop:

sf::Texture texture;
if (!texture.loadFromFile("assets/enemy.png")) {
  std::cout << "Could not load enemy texture" << std::endl;
  return 0;
}

This will create a variable of type sf::Texture and load the image into it. If the load fails, we print an error message and return. Sometimes, the load for an asset fails for some unknown reason so we should handle any errors properly. You will need to #include <iostream> at the top of main.cpp as well. Once we have the texture, we can create a sprite object called enemySprite and pass in the texture like this:

sf::Sprite enemySprite;
enemySprite.setTexture(texture);

The sprite will only be as big as the image provided and will default to be at position (0,0) or in the upper left corner. We can change the position like this:

enemySprite.setPosition(sf::Vector2f(100,100));

Which brings the sprite 100 pixels out from the left and 100 pixels out from the right and increase the size of the sprite by scaling it like this:

enemySprite.scale(sf::Vector2f(1,1.5));

This will scale the width of the sprite by 1 (no change) and scale the height to 1.5x its original height. Notice how both functions take an sf::Vector2f as inputs and each needs an x and y value. In order to draw the sprite, we change the draw code to this:

window.clear();
window.draw(enemySprite);
window.display();

We always have to clear the window before drawing anything and display the window after we draw to it.

Did you come across any errors in this tutorial? Please let us know by completing this form and we’ll look into it!

FREE COURSES
Python Blog Image

FINAL DAYS: Unlock coding courses in Unity, Godot, Unreal, Python and more.

Transcript

What’s up everyone? Welcome to our tutorial on Drawing Sprites. Here we’ll get a quick intro into what sprites are from a game context and how to create and use them in SFML.

So this is actually a two step process, the first thing we need to do is create a texture object. Once we have that we can create a sprite from it and then we can set the position and the scale. So let’s head to the code and get started. Alright, so just a quick heads up again, I took all the code from the previous section, not that we really did very much and put it in old code and I’ll continue to do this with each new section.

Alright, so what is a sprite from a game context? Well essentially, a sprite is gonna be an object in the game that has an image associated with it. So this is really the main difference between let’s say shapes and sprites in games is that a sprite has an image and a shape just has well a shape. It just has its boundaries, it has some sort of code to dictate what shape those boundaries will take on, be of circles, square, rectangle, etc.

So in our case, the background of our game and the enemy itself, those are both going to be sprites, we’re not really gonna be working with shapes very much. So like I said this is a two step process. The first thing we need to do is load in a texture and a texture needs an image to load. So that’s why I had you load in your assets folder. So your project should look like this, sfml project, you have your codes, and then you have your assets folder with the items in it. We’ll use the ttf as a font later on. Same with the damage.ogg, that’s for sound. For now we’ll at least want the enemy.png because that’s what we’re gonna be working with here. Okay, so as long as we have it in our project assets /enemy.png, then we can load it in like this.

Okay, first thing that we’ll need to do is create a texture itself so we’ll do sf, Texture, texture. Okay, now a texture just like the Render Window is part of the SFML Graphics library. Anytime you need a new module, you’ll need to load it in here. Okay, so we have a texture object, we actually don’t need to call a constructor, set it equal to a texture or anything like that. Once we create the object, we have access to it immediately and we need to call the load from file function, like this texture.load From file, oops! Not load from stream we want load from file.

Okay, and then we’re going to pass in the path to the file. So in this case this is gonna be “assets/ “enemy “.png”. Now this is actually gonna return true or false based on the success or failure. So we’re gonna say something like if text actually, we’ll say if not texture.load from file, then maybe we’ll just print out some message and return. So let’s just close that off and this should actually be in here.

Okay, so in this case, what we can do is something like Standard c out, I actually don’t think we have the iOS stream library so I’m just gonna include that now. Include your stream. Okay, good stuff. Okay, so now what we’ll do is c out something like “Could not load, “enemy texture”. Okay, and then we’re just going to end it.

All right and because we really want the game to only run if the texture is loaded, we’re actually gonna return false. Cool, so as long as this is the case oh actually you know what? This is returning will turn zero. Okay, so as long as the texture is loaded, so as long as this doesn’t return zero, then we have a texture rather an image loaded into this texture, and now we can use it with a Sprite. So to do that, we’ll do basically the same process as with the texture, we need to create the sprite object first, Sprite and we’ll call this like enemySprites or something.

Okay, and then we’re going to call upon the enemySprite . setTexture function and then we’re I’m just going to pass in the texture that we loaded. Okay, so this will associate a texture with a Sprite. So now the sprite is created It has a texture and we can draw it. We don’t know exactly what size or position well we do know what position it will be in which will be 00 by default which will be upper left corner and the size will be exactly the size of the image itself. We can modify that later on, and which we’ll do in just a minute here.

Okay, so just using the default values, if we want to draw this to the window, we simply call upon the window.draw and then pass in the Sprite. So in this case, enemySprite. Okay, cool. So we’ll get this Save, and let’s run the code, let’s see what happens. So clear it, let’s compile it, and then let’s run it and now you can see that we have this little sprite in our game.

Obviously there are some issues here it’s getting cut off so the screen is not big enough to begin with. Also, this is kind of in the top left corner, we might not want it there and might not be quite big enough. Okay, so this is all stuff that we can just maybe let’s do a 500 by 500 window. That way we have enough size to draw most of the things that we need. Then if we go to rerun it, we should probably see that’s not gonna take up the whole screen anymore. It’s just take up a part of it. So maybe we don’t want it in the top left. Maybe we want it kind of a bit centered.

So what we can do is maybe move it about 100 pixels to the right and 100 pixels down, might put it roughly in the center, okay. So what we can do is take this enemy sprite, enemySprite, okay and we can set the position of it. So, this is gonna take in an a Vector two f object like this SF Vector two f which will take in a vector two dimensional float, and this will need a width and a height or an X and Y value. So in this case, we’ll just do a 100 and 100. Okay, if we go to lets close this off, we go to rerun it.

Okay, so recompile it, again, every time you make a change, you have to recompile it, you can see that this has now moved, we can also change the height, let’s kind of make this guy a little bit taller, but we won’t necessarily change the width of it. So what we can do is lets close that up do the enemySprite . And we can scale it. Okay, weirdly enough, you can’t assign a specific width and height, you actually have to scale things.

Okay, so in this case, we’re going to again pass in a vector2f, capital V, Vector two f, okay and then we’re going to pass in the amount by which we want to scale the x and the amount by which we want to scale the y. So the x is going to remain exactly the same. So we’ll just do one, the y however, we want to change the height, maybe we’ll do like a 1.5 and see how that works out.

Okay, so we’ll go back to here. Well, I guess we don’t need to clear it. We’ll just kind of recompile and we’ll rerun it and now you can see that this guy is horribly stretched, but at least the scaling worked. Now there are plenty of other things that we can do with Sprites but this will be pretty much the extent of what we’re gonna do in this course with our Sprites.

One last thing to note before moving on to the next section is that the sprites bounding box is actually this whole rectangle. Weirdly enough, the bounding box doesn’t follow the image like this. This is gonna be the bounding box. So when when it comes to detecting mouse clicks on the sky, even if you click up here, it’s technically within the bounding box. So that’s going to register a click. Okay, we’ll get more into that a little bit later on. Just wanted to make you guys aware now. Okay, we’ll close this up.

Otherwise, that’s it. So in this section, we covered two things, loading in textures, and the second creating sprites and assessing their attributes. Definitely Feel free to play around with this. Maybe try to load in your background. See how well you can do with that. When you’re ready to move on, we’ll do pretty much the same thing but with text. So stay tuned for that. Thanks for watching and see you guys in the next one

Interested in continuing? Check out the full Discover SFML for C++ Game Development course, which is part of our C++ Programming Bundle.