#include "SFML\Window.hpp"
#include "SFML\System.hpp"
#include "SFML\Graphics.hpp"
#include <algorithm>
#include <deque>
// Base object
class Object : public sf::Drawable
{
public:
virtual void draw(sf::RenderTarget&, sf::RenderStates) const = 0;
bool is_deleted;
};
// Derived object
class Square : public Object
{
sf::RectangleShape square;
public:
Square(sf::Vector2f position)
{
square.setFillColor(sf::Color::Green);
square.setSize(sf::Vector2f(20, 20));
square.setPosition(position);
is_deleted = false;
}
void draw(sf::RenderTarget& target, sf::RenderStates state) const
{
target.draw(square, state);
}
};
int main()
{
sf::RenderWindow window(sf::VideoMode(800, 600), "Test", sf::Style::Default);
sf::Event eve;
// Initialising objects and putting them into containters
std::deque<Square> square_deque;
Square square_1(sf::Vector2f(100, 25));
square_deque.push_back(square_1);
Square square_2(sf::Vector2f(100, 50));
square_deque.push_back(square_2);
Square square_3(sf::Vector2f(100, 75));
square_deque.push_back(square_3);
// Seperate deque that contains pointers of base class - pointers take adresses of derived objects and are stored for later drawing.
// Doing so, I can store different types of objects into the deque who share the same parent class.
Object* ptr;
std::deque<Object*> objects_for_draw;
for (unsigned int i = 0; i < square_deque.size(); ++i)
{
ptr = &square_deque.at(i);
objects_for_draw.push_back(std::move(ptr));
}
while (window.isOpen())
{
while (window.pollEvent(eve))
{
if (eve.type == sf::Event::Closed)
window.close();
if (eve.type == sf::Event::KeyPressed)
{
if (eve.key.code == sf::Keyboard::Space)
{
// When space is pressed, the second square is marked for deletion.
// Then the object is being evaluated in lambda expression whether the 'is_deleted' bool true.
// If it is, then it's removed from both deque containters.
square_deque.at(1).is_deleted = true;
objects_for_draw.erase(std::remove_if(objects_for_draw.begin(), objects_for_draw.end(), [&](Object* param) { return param->is_deleted; }), objects_for_draw.end());
// Here is a second deque container from which the object should be removed.
// Unfortunetaly, when it is removed, the " Pure virtual function call" error occurs later.
// When this is commented out, the program runs fine - but object still exists and can interact. It is simply not drawn anymore
square_deque.erase(std::remove_if(square_deque.begin(), square_deque.end(), [&](Square param) { return param.is_deleted; }), square_deque.end());
}
}
}
window.clear(sf::Color(63,63,63,255));
for (const auto& it : objects_for_draw)
window.draw(*it); // The program breaks here (or at least the breakpoint points here), with error message "R6025 - Pure virtual function called"
window.display();
}
return 0;
}