46
Feature requests / Re: Ostream operators << for SFML classes
« on: March 20, 2014, 09:33:45 am »
Without further ado:
(Four operators implemented for demonstration purposes)
Drawback: cannot be used to output built-in or non-sfml types
Example usage:
Output:
It's easy to have it output to a fstream or stringstream instead.
The ctor is public so the user can make a persistent Debug object if they wish.
Not the point.
namespace sf {
class Debug {
public:
Debug (std::ostream& sink = std::cout):
m_stream(sink)
{
}
template <typename T>
Debug& operator<<(const sf::Vector2<T>& vector) {
m_stream << "Vector(" << vector.x << ", " << vector.y << ")\n";
return *this;
}
template <typename T>
Debug& operator<<(const sf::Rect<T>& rect) {
m_stream << "Rect(" << rect.left << ", " << rect.top << ", " << rect.width << ", " << rect.height << ")\n";
return *this;
}
Debug& operator<<(const sf::Transform& transform) {
const float* matrix = transform.getMatrix();
m_stream << "Transform:\n";
for (int i=0; i<4; ++i){
m_stream << "( ";
for (int j=0; j<4; ++j)
m_stream << matrix[i*4 + j] << " ";
m_stream << ")\n";
}
return *this;
}
Debug& operator<<(const sf::Sprite& sprite) {
m_stream << "Sprite: ";
operator<<(sprite.getGlobalBounds());
return *this;
}
~Debug() {
m_stream.flush();
}
private:
std::ostream& m_stream;
};
Debug debug(std::ostream& sink = std::cout) {
return Debug(sink);
}
}
class Debug {
public:
Debug (std::ostream& sink = std::cout):
m_stream(sink)
{
}
template <typename T>
Debug& operator<<(const sf::Vector2<T>& vector) {
m_stream << "Vector(" << vector.x << ", " << vector.y << ")\n";
return *this;
}
template <typename T>
Debug& operator<<(const sf::Rect<T>& rect) {
m_stream << "Rect(" << rect.left << ", " << rect.top << ", " << rect.width << ", " << rect.height << ")\n";
return *this;
}
Debug& operator<<(const sf::Transform& transform) {
const float* matrix = transform.getMatrix();
m_stream << "Transform:\n";
for (int i=0; i<4; ++i){
m_stream << "( ";
for (int j=0; j<4; ++j)
m_stream << matrix[i*4 + j] << " ";
m_stream << ")\n";
}
return *this;
}
Debug& operator<<(const sf::Sprite& sprite) {
m_stream << "Sprite: ";
operator<<(sprite.getGlobalBounds());
return *this;
}
~Debug() {
m_stream.flush();
}
private:
std::ostream& m_stream;
};
Debug debug(std::ostream& sink = std::cout) {
return Debug(sink);
}
}
(Four operators implemented for demonstration purposes)
Drawback: cannot be used to output built-in or non-sfml types
Example usage:
sf::debug() << sf::Vector2f(10, 10) << sf::Vector2f(20, 20); //output to cout by default
sf::Sprite sprite;
sf::debug(std::cerr) << sprite << sprite.getTransform(); //outputs to cerr
sf::Sprite sprite;
sf::debug(std::cerr) << sprite << sprite.getTransform(); //outputs to cerr
Output:
Code: [Select]
Vector(10, 10)
Vector(20, 20)
Sprite: Rect(0, 0, 0, 0)
Transform:
( 1 0 0 0 )
( -0 1 0 0 )
( 0 0 1 0 )
( 0 0 0 1 )
It's easy to have it output to a fstream or stringstream instead.
The ctor is public so the user can make a persistent Debug object if they wish.
Quote
why on earth would someone ever want to save a whole sprite, or even worse a texture directly to a file?
Not the point.