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

Auteur Sujet: Optimisation - Effet de lumière  (Lu 4558 fois)

0 Membres et 1 Invité sur ce sujet

Sutat

  • Newbie
  • *
  • Messages: 6
    • Voir le profil
    • E-mail
Optimisation - Effet de lumière
« le: Février 02, 2013, 04:09:00 pm »
Bonjour,

J'aimerais développer un petit jeu en 2D basé sur des effets de lumière.
Ca fait très longtemps que je n'ai pas développé en C++, je me suis souvenu que je jouais avec la SFML et que j'aimais bien donc je l'ai reprise, j'utilise la 2.0.

Voilà pour la petite histoire.
Mon problème est que j'ai l'impression que ma méthode pour faire mes effets de lumière va être très très gourmande quand je vois la petite maquette que je viens d'écrire.

Ma question est donc : avez-vous des axes d'optimisation ?

J'utilise deux RenderTexture :
  • gameTexture : Pour les sprites du jeu
  • blendTexture : Pour les effets de lumière

En gros je dessine mon jeu dans la gameTexture.
Puis mes effets de transparence en niveau de gris dans la blendTexture.
Je dessine la blendTexture sur le RenderWindow, puis la gameTexture en "BlendMultiply".

Ce qui donne :
blendTexture.clear();
        blendTexture.draw(rectangle);
        blendTexture.setSmooth(true);

        for (float radius = 1000.0f; radius > 200.0f; radius -= 2.0f) {
            sf::CircleShape circle(radius);
            int black = -0.30625 * radius + 316.25; // Droite
            circle.setFillColor(sf::Color(black, black, black));
            circle.setPointCount(radius/10);
            circle.setPosition(pos.x - radius, pos.y - radius);
            blendTexture.draw(circle);
        }

        blendTexture.display();

        gameTexture.clear();
        gameTexture.draw(sprite);
        gameTexture.display();

        sf::Sprite blend(blendTexture.getTexture());
        sf::Sprite game(gameTexture.getTexture());

        window.clear();
        window.draw(blend);
        window.draw(game, sf::BlendMultiply);
        window.display();
 

J'ai mis en pièce jointe le petit fichier de source complet de la maquette si ça intéresse.
Si vous voulez tester il faut mettre une image "115869.jpg" qui fait 1920x1080 (si votre résolution supporte) pour lancer l'application.

Merci,

[attachment deleted by admin]

Laurent

  • Administrator
  • Hero Member
  • *****
  • Messages: 32504
    • Voir le profil
    • SFML's website
    • E-mail
Re : Optimisation - Effet de lumière
« Réponse #1 le: Février 02, 2013, 05:00:36 pm »
Et qu'est-ce qui est censé être gourmand là-dedans ? Je ne vois rien de spécial.
Laurent Gomila - SFML developer

Sutat

  • Newbie
  • *
  • Messages: 6
    • Voir le profil
    • E-mail
Re : Optimisation - Effet de lumière
« Réponse #2 le: Février 02, 2013, 05:28:31 pm »
Je dessine autant de cercle que de dégradé de lumière pour un faisceau de lumière et pour chaque frame.
Je pense que le problème vient de là.

Quand on lance l'application on ressent vraiment que ça ram, la lumière à du mal à suivre ma souris.
J'ai la solution de précalculer le cercle de lumière, mais ce sera moins joli si je zoom beaucoup.

Après sans parler de ça, est-ce que tu penses que c'est une bonne solution de passer par deux RenderTexture.
J'ai lu des topics qui parlent de post-fx mais je ne sais pas si ça vaut le coup pour ça.

Laurent

  • Administrator
  • Hero Member
  • *****
  • Messages: 32504
    • Voir le profil
    • SFML's website
    • E-mail
Re : Optimisation - Effet de lumière
« Réponse #3 le: Février 02, 2013, 06:20:01 pm »
Citer
Je dessine autant de cercle que de dégradé de lumière pour un faisceau de lumière et pour chaque frame.
Ah oui... Pourquoi ne pas plutôt utiliser un seul cercle rempli avec un dégradé de couleurs ?

Citer
Après sans parler de ça, est-ce que tu penses que c'est une bonne solution de passer par deux RenderTexture.
Le concept est bon, mais ton algorithme est bizarre. Normalement on dessine la scène directement sur la fenêtre puis on applique une surface contenant les effets de lumière en mode BlendMultiply. Je ne comprends pas ta façon de faire, peux-tu expliquer ?

Citer
J'ai lu des topics qui parlent de post-fx mais je ne sais pas si ça vaut le coup pour ça.
Les shaders (post-fx = shader sur tout l'écran) ne sont qu'un moyen de court-circuiter ce que fait la carte graphique. Donc tant que tu peux implémenter ton algorithme avec des trucs standards, et que ça ne requiert pas des opérations ridiculement lentes (genre accéder à une texture pixel par pixel), alors ça ne t'apportera rien de réimplémenter le truc avec un shader.
Laurent Gomila - SFML developer

Sutat

  • Newbie
  • *
  • Messages: 6
    • Voir le profil
    • E-mail
Re : Re : Optimisation - Effet de lumière
« Réponse #4 le: Février 02, 2013, 07:52:10 pm »
Ah oui... Pourquoi ne pas plutôt utiliser un seul cercle rempli avec un dégradé de couleurs ?
Je le fais avec la solution précalculée. Mais sinon je ne sais pas comment on fait un dégradé de couleur avec SFML, je regarderais.

Citer
Le concept est bon, mais ton algorithme est bizarre. Normalement on dessine la scène directement sur la fenêtre puis on applique une surface contenant les effets de lumière en mode BlendMultiply. Je ne comprends pas ta façon de faire, peux-tu expliquer ?
En fait j'ai deux surfaces : la surface en niveau de gris et la surface de la scène (le jeu avec des sprites).
Ce que je fais c'est dessiner la surface de la scène APRES le niveau de gris en mode BlendMultiply.
Je le fais dans le sens contraire de ce que tu proposes.

Je viens de tester ce que tu proposes et ça fonctionne, je ne sais pas pourquoi je voyais ça dans l'autre sens, mais tu me diras une multiplication fonctionne dans les deux sens : a*b = b*a. :)

Je vais prendre ta solution, on utilise un RenderTexture en moins.

Citer
Les shaders (post-fx = shader sur tout l'écran) ne sont qu'un moyen de court-circuiter ce que fait la carte graphique. Donc tant que tu peux implémenter ton algorithme avec des trucs standards, et que ça ne requiert pas des opérations ridiculement lentes (genre accéder à une texture pixel par pixel), alors ça ne t'apportera rien de réimplémenter le truc avec un shader.
Très bien merci.

Laurent

  • Administrator
  • Hero Member
  • *****
  • Messages: 32504
    • Voir le profil
    • SFML's website
    • E-mail
Re : Optimisation - Effet de lumière
« Réponse #5 le: Février 02, 2013, 08:38:14 pm »
Citer
Mais sinon je ne sais pas comment on fait un dégradé de couleur avec SFML, je regarderais.
Avec un vertex array, qui te permet de définir la couleur de chaque sommet. Pour faire un cercle, je ferais un vertex array en mode TriangleFan : 1er vertex au centre, avec la couleur centrale, puis les points du contour dans l'ordre, avec la couleur du contour. Ca te fera un beau dégradé du centre vers le bord.
« Modifié: Février 08, 2013, 08:40:57 pm par Laurent »
Laurent Gomila - SFML developer

Lolilolight

  • Hero Member
  • *****
  • Messages: 1232
    • Voir le profil
Re : Optimisation - Effet de lumière
« Réponse #6 le: Février 03, 2013, 10:01:32 am »
Ha en parlant de ça il va falloir que j'optimise le mien, je ne sais pas si c'est plus optimisé d'utilisé des demi-cercle plutôt que des triangles, je parle surtout si la lumière est coupée par un mur, je pense pas que c'est possible de dessiner des demi-cercles en dégradé avec la SFML (ou bien avec openGL) de toute façon, mais j'avais lu un article une fois ou il y en avait un qui faisait comme ça avec le stencil buffer de la SFML mais il faudrait que je retrouve l'article. :/

Laurent

  • Administrator
  • Hero Member
  • *****
  • Messages: 32504
    • Voir le profil
    • SFML's website
    • E-mail
Re : Optimisation - Effet de lumière
« Réponse #7 le: Février 03, 2013, 11:17:40 am »
A bas niveau tu ne peux rien dessiner d'autre que des points, des lignes et des triangles. Donc quoique tu veuilles dessiner, ce sera à base de triangles.
Laurent Gomila - SFML developer

Gregouar

  • Sr. Member
  • ****
  • Messages: 462
  • www.holyspirit.fr : free hack'&'slash
    • Live Messenger (MSN) - Greg_le_sadique@hotmail.com
    • Voir le profil
    • www.holyspirit.fr
    • E-mail
Re : Optimisation - Effet de lumière
« Réponse #8 le: Février 04, 2013, 12:02:24 pm »
Ce n'est plus trop à jour avec la SFML2 je pense, mais ça pourrait peut-être te donner des idées : http://gregouar.developpez.com/tutoriels/jeux/moteur-lumieres-dynamiques-2d/

Sutat

  • Newbie
  • *
  • Messages: 6
    • Voir le profil
    • E-mail
Re : Optimisation - Effet de lumière
« Réponse #9 le: Février 08, 2013, 08:39:11 am »
Bon j'ai fais un vertex Array pour faire ma lumière en TriangleStrip.
C'est vrai que le dégradé est bien, mais si je veux faire des lumières d'une forme précise ça va vraiment pas être simple à la longue.

Je vais pour l'instant rester sur mes images précalculées, mais je garde ça de coté dans ma branche git :)

@Gregouar Le lien que tu m'as donné m'a pas mal inspiré.

Merci,

Voici la formule que j'utilisais pour construire un triangle, c'était pas super, j'avais des fois des points blanc qui apparaissait dans mon cercle, et des fois il y a un triangle en trop dans le cercle qui en superpose un autre :
        quarter = (360.0f / nbTriangles);
        for (float angle = 0.0f; angle <= 360.0f; angle += quarter)
        {
            va.append(center);
            va.append(sf::Vertex(sf::Vector2f(rayon * cosf(angle * PI / 180) + x, rayon * sinf(angle * PI / 180) + y), couleurExtremite));
            va.append(sf::Vertex(sf::Vector2f(rayon * cosf((angle + quarter) * PI / 180) + x, rayon * sinf((angle + quarter) * PI / 180) + y), couleurExtremite));
            va.append(sf::Vertex(sf::Vector2f(rayon * coeffIntermediaire * cosf(angle * PI / 180) + x, rayon * coeffIntermediaire * sinf(angle * PI / 180) + y), couleurIntermediaire));
            va.append(sf::Vertex(sf::Vector2f(rayon * coeffIntermediaire * cosf((angle + quarter) * PI / 180) + x, rayon * coeffIntermediaire * sinf((angle + quarter) * PI / 180) + y), couleurIntermediaire));
        }
        va.append(center);
 
« Modifié: Février 08, 2013, 09:21:22 am par Laurent »

Lolilolight

  • Hero Member
  • *****
  • Messages: 1232
    • Voir le profil
Re : Optimisation - Effet de lumière
« Réponse #10 le: Février 08, 2013, 09:25:56 am »
Pour ma part je pense que je vais utiliser des triangles fan pour l'optimisation à la place de triangles, vu que ils ont tous un sommets commun : le centrze de la lumière.

http://en.wikipedia.org/wiki/Triangle_fan

Au sinon tu peux toujours faire cela avec des images préconçues (le light mappping par exemple.), mais je sais pas trop t'en dire plus à ce niveau là car je n'ai jamais essayer de faire ça pour de la 2D.
Mais il doit y avoir moyen : http://mdeverdelhan.developpez.com/tutoriel/dynamiclight/tutoriel2/





Sutat

  • Newbie
  • *
  • Messages: 6
    • Voir le profil
    • E-mail
Re : Optimisation - Effet de lumière
« Réponse #11 le: Février 08, 2013, 06:42:51 pm »
Quand je parle d'images pré calculées plus haut ce sont bien des images PNG que je fais sur gimp.
Ca marche plutôt bien, mais je dois prévoir des tailles de PNG différentes je pense si je veux beaucoup faire varier la taille de ma lumière.

Sinon c'est intéressant le TriangleFan, je ne connaissais pas non plus le TriangleStrip avant que Laurent m'en parle. A voir si ça marche bien pour faire un cercle composé d'autres cercles.. ce que j'ai fais dans mon petit bout de code, pour avoir plus de choix de dégradés.