I have tried for many hours and failed to get this working. I have
redefined the class and it does compile - but it does not do exactly as
the 'non class' code below does.
Below is the test program that simply displays a sprite and moves it up
the y axis following a press of the left shift key. Now the sfml stuff
is not really important to my problem but i include it for completeness.
1 - original program - does not use class
#include <iostream>
#include<SFML/Graphics.hpp>
#include<SFML/System.hpp>
int main()
{
// sfml stuff - not relevant here
sf::RenderWindow mywindow(sf::VideoMode(800,600), "missile testing",
sf::Style::Fullscreen);
mywindow.setVerticalSyncEnabled(true);
// THIS IS THE SECTION I WANT TO PUT INTO A CLASS MISSILE
sf::Texture rocket_picture;
rocket_picture.loadFromFile("/home/game/images/missile.jpg");
sf::Sprite missile;
missile.setTexture(rocket_picture);
missile.setScale(0.2f,0.2f);
missile.setPosition(350,400);
//END OF SECTION
// sfml stuff not relevant here
sf::Vector2f position(400,500);
sf::Vector2f pos(400,500);
sf::Time elapsed;
sf::Clock clock;
bool firemissile= false;
bool running = true;
while(mywindow.isOpen())
{
elapsed = clock.restart();
pos = missile.getPosition();
sf::Event event;
while (mywindow.pollEvent(event))
{
if((event.type == sf::Event::KeyPressed) && (event.key.code ==
sf::Keyboard::Escape))
mywindow.close();
if((event.type == sf::Event::KeyPressed) && (event.key.code ==
sf::Keyboard::LShift))
{
// fire 1 missile!
firemissile = true;
}
}
if(firemissile)
{
if(pos.y >= 10)
// NEEDS TO BE A MEMBER FUNCTION
missile.move(0, -200 * elapsed.asSeconds() );
}
mywindow.clear();
mywindow.draw(missile);
mywindow.display();
} // while window is open
return EXIT_SUCCESS;
}//main
-------------------------------
Ok - so the above code works. But what i am seeking to do is to create a
class called 'missile'. This class - will only have one function:
missile.move(0, -200 * elapsed.asSeconds() );
Now the class missile simply represents a sprite. The code that creates
and initialises a sprite in sfml are these few lines:
sf::Texture rocket_picture;
rocket_picture.loadFromFile("/home/game/images/missile.jpg");
sf::Sprite missile;
missile.setTexture(rocket_picture);
missile.setScale(0.2f,0.2f);
missile.setPosition(350,400);
There are two sfml (c++) classes here namely sf::Texture and sf::Sprite.
loadFromFile is a member function of Texture.
setTexture, setScale and setPosition are member functions of sf::Sprite.
Each of these classes has numerous other member functions as well.
So the first step in creating my class is to make sure that it inherits
from these base classes. This is right, isn't it?
I got into a terrible mess on my first attempt and spent a lot of time
trying to correct what i did wrong. This is the re-write I did of the
class missile in a file called missile.h
2. Class missile
#ifndef MISSILE_H
#define MISSILE_H
#include<SFML/Graphics.hpp>
#include<SFML/System.hpp>
class missile : public sf::Sprite, sf::Texture
{
public:
missile()
{
sf::Texture rocket_picture;
rocket_picture.loadFromFile("/home/game/images/missile.jpg");
rocket.setTexture(rocket_picture);
rocket.setScale(0.2f,0.2f);
rocket.setPosition(350,400);
}
private:
static sf::Texture rocket_picture;
sf::Sprite rocket;
};
#endif
Basically - this class should incorporate all the data that is in the
original program concerning the missile. I just wanted to concentrate on
getting it to work and left out the only public member function -
'move()' until i get it working.
Now I wrote another test program to act as a driver to see if i could
use this class.
3. Driver program for class missile
// test of missile class
#include <iostream>
#include<SFML/Graphics.hpp>
#include<SFML/System.hpp>
#include "missile.h"
int main()
{
// sfml stuff
sf::RenderWindow mywindow(sf::VideoMode(800,600),"missile test",
sf::Style::Fullscreen);
mywindow.setVerticalSyncEnabled(true);
// object created
missile mymissile;
// sfml stuff
sf::Vector2f position(400,500);
sf::Vector2f pos(400,500);
sf::Time elapsed;
sf::Clock clock;
bool firemissile= false;
bool running = true;
while(mywindow.isOpen())
{
elapsed = clock.restart();
pos = mymissile.getPosition();
std::cout << pos.x << "x" << pos.y << std::endl;
sf::Event event;
while (mywindow.pollEvent(event))
{
if((event.type == sf::Event::KeyPressed) && (event.key.code ==
sf::Keyboard::Escape))
mywindow.close();
if((event.type == sf::Event::KeyPressed) && (event.key.code ==
sf::Keyboard::LShift))
{
// fire 1 missile!
firemissile = true;
}
}
if(firemissile)
{
// NOT IMPLEMENTED
// if(pos.y >= 10)
//mymissile.move(0, -200 * elapsed.asSeconds() );
}
mywindow.clear();
mywindow.draw(mymissile);
mywindow.display();
} // while window is open
return EXIT_SUCCESS;
}//main
-------------------
I compile this program with
g++ -std=c++11 missile_class_test.cpp -o cmissile -lsfml-graphics
-lsfml-window -lsfml-system
There are no compile errors and the program runs - but it just displays
a blank screen - it does not show the sprite. Therefore the class does
not do exactly what the code in the original program did.
I had problems understanding how to initialize the data members of the
class because in the books on c++ the examples of constructors do not
show multiple lines of code like this. Is the constructor the problem here?
The output of
std::cout << pos.x << "x" << pos.y << std::endl; is 0x0 when run. This
means that the line in the constructor that is >
rocket.setPosition(350,400);
has no effect.
I do not undersatnd why there are no error messages being generated.
In any case can you see where i have gone wrong in defining this class?