Bienvenue, Invité. Merci de vous connecter ou de vous inscrire.
Avez-vous perdu votre e-mail d'activation ?

Auteur Sujet: Passage de plusieurs sf::Text sur une sf::RenderTexture [SFML 2.0]  (Lu 1775 fois)

0 Membres et 1 Invité sur ce sujet

DrPapino

  • Newbie
  • *
  • Messages: 34
    • Voir le profil
Bonjour, j'essaie de créer une console pour mon petit programme, comme sur cette image :
http://www.legendra.com/media/screenshots/pc/baldur__s_gate/screen_10.jpg

Pour pouvoir faire des mots de différentes couleurs sur une même ligne, j'utilise un pair de sf::Text. Un deque contient ces pair, chaque élément du deque représentant une ligne.

Cette console est donc un champ de texte et pour faire défiler ce texte, il me faudrait une slidebar. Je suis donc parti sur l'idée suivante : je crée une sf::RenderTexture sur laquelle je dessine tous mes sf::Text, je passe cette renderTexture sur un sprite et ensuite, pour faire défiler mon texte, j'utiliserai la méthode setTextureRect. C'est un peu barabare, je préfèrerai ne pas avoir à passer par une renderTexture, si vous avez une autre idée je suis bien sûr preneur..

Voici donc ma classe Console :

Console.h
class Console : public sf::Drawable, public sf::Transformable
{
public:
   
    Console();
       
    void type(std::string string1, std::string string2 = " ");
   
    void setColors(sf::Color color1, sf::Color color2 = sf::Color::White);

    void clear();

    void finalize();
       
private:
   
    std::deque<std::pair<sf::Text,sf::Text> > lines;
   
    std::pair<sf::Text,sf::Text> line;
   
    sf::Font font;
       
    int lineSpacing;
   
    sf::RectangleShape textField;

    sf::RenderTexture renderTexture;
   
    sf::Sprite sprite;
   
private:
   
    virtual void draw(sf::RenderTarget& target, sf::RenderStates states) const;
};

Console.cpp
Console::Console()
{
    font.loadFromFile("/Users/HéhéVousSaurezPaaas/Desktop/Data Files/Font/Chantelli_Antiqua.ttf.ttf");
   
    line.first.setFont(font);
   
    lineSpacing = font.getLineSpacing(12)-3; // -3 = pour rapprocher les lignes entre elles

    line.first.setCharacterSize(12);
   
    line.second.setCharacterSize(12);

    line.second.setFont(font);
   
    textField.setSize(sf::Vector2f(700,100));
   
    textField.setFillColor(sf::Color(0,0,0,175));
}


void Console::draw(sf::RenderTarget& target, sf::RenderStates states) const
{
    states.transform *= getTransform();
   
    target.draw(textField, states);
   
    /*
    for (int i=0; i<lines.size(); i++)
    {
        target.draw(lines[i].first, states);
        target.draw(lines[i].second, states);
    }
    */


    target.draw(sprite, states);
}


void Console::type(std::string string1, std::string string2)
{
    // On commence par assigner les chaines de caractère
    line.first.setString(string1);

    if (string2 == " ")
    {
        string2.clear();
    }
   
    line.second.setString(string2);
   
    // Puis on gère les positions : si c'est la première ligne qu'on écrit
    if (lines.empty())
    {    
        // on la palce en (0,0)
        line.first.setPosition(0,0);
    }
   
    // Sinon
    else
    {
        // Il faut revenir à la ligne
        line.first.setPosition(0,lines.size()*lineSpacing);
    }
   
    line.second.setPosition(line.first.getGlobalBounds().width,line.first.getPosition().y);
   
    lines.push_back(line);
}

void Console::setColors(sf::Color color1, sf::Color color2)
{        
    lines.back().first.setColor(color1);
   
    lines.back().second.setColor(color2);
}

void Console::finalize()
{
    renderTexture.create(700,300);
   
    renderTexture.clear(sf::Color::Transparent);
   
    for (int i=0; i<lines.size(); i++)
    {
        renderTexture.draw(lines[i].first);
        renderTexture.draw(lines[i].second);
    }
   
    renderTexture.display();
   
    sprite.setTexture(renderTexture.getTexture());
}

void Console::clear()
{
    lines.clear();
}

Et un petit exemple d'utilisation :
Console console;
   
   
   
    console.type("Bonjour", "je");
   
    console.setColors(sf::Color::Yellow, sf::Color::Green);
   
    console.type("suis le ", "capitaine sur ce navire");
 console.setColors(sf::Color::Blue);

    console.finalize();

// boucle du jeu...
window.draw(console);

 

Ce code ne marche pas, bien entendu, et cette méthode finalize() et appelée à disparaitre, du moins je l'espère.. Après des tests, j'ai compris que la partie "renderTexture.clear, renderTexture.draw, renderTexture.display()" devait se faire à chaque boucle, il serait donc logique de faire ces étapes dans la fonction draw mais puisqu'elle est const, je suis un peu embêté.

Tel quel, ce code donne un texte très flou, c'est même pas du flou en fait, c'est plus des barres, de même longueur et de même couleur que les mots. Pas vraiment exploitable, donc ^^

Comment faire ?

Merci de vos réponses.