Welcome, Guest. Please login or register. Did you miss your activation email?

Author Topic: Blinking sprites, draw on click.  (Read 2998 times)

0 Members and 1 Guest are viewing this topic.

lowarago

  • Newbie
  • *
  • Posts: 10
    • View Profile
Blinking sprites, draw on click.
« on: March 26, 2017, 12:51:54 am »
Hello, I am trying to make better perfomance of my level editor a little better so while I am idle (not doing anything on window (pressing keys, spawning objects)) I want to draw the sprites to window and then wait for another click.

After I click again I want to spawn object on window, draw_everything_again(), win.display() but this causes blinking sprites. It actually draws them on correct places but they are blinking.


auto draw_map = [&win_editor] (const std::vector<std::vector<char>>& map, sf::Sprite wall_spr) {
                                                               
                                                                for (int i = 0; i < map.size(); i++) {
                                                                        //Go
                                                                        for (int j = 0; j < map[0].size(); j++) {
                                                                                if (map[i][j] == '*') {
                                                                                        wall_spr.setPosition(sf::Vector2f(i*gm_win.N, j*gm_win.N));
                                                                                        win_editor.draw(wall_spr);
                                                                                }
                                                                        }

                                                                }
                                                        };

bool btn_pressed = false;

while (win_editor.isOpen()) {
                                                               
  while (win_editor.pollEvent(some_events)) {
                                                                       
   //WINDOW IS OPENED
                                                                        switch (some_events.type) {

                                                                        case sf::Event::Closed:

                                                                                //Maybe ask for save safe;
                                                                                win_editor.close();

                                                                                break;
                                                                        case sf::Event::MouseButtonPressed:

                                                                                //Just perfomance stuff, we don't need to refresh window everytime, just when we do actions
                                                                                btn_pressed = true;
                                                                                break;
                                                                        }
                                                                       
                                                                       

                                                                       
                                                                } //End of while

                                                                if (btn_pressed) {
                                                                        win_editor.clear(sf::Color::Black);
                                                                        draw_map(editors_map, temp_spr);
                                                                        btn_pressed = false;
                                                                }

                                                                win_editor.display();
                                                        }
 

« Last Edit: March 26, 2017, 12:53:42 am by lowarago »

Hapax

  • Hero Member
  • *****
  • Posts: 3379
  • My number of posts is shown in hexadecimal.
    • View Profile
    • Links
Re: Blinking sprites, draw on click.
« Reply #1 on: March 26, 2017, 01:01:06 am »
The window should be cleared, drawn, and displayed every cycle of the loop, whether or not it has changed.

Incidentally, display() swaps the back buffer with the visible screen which causes the flickering.

Quote from: SFML's "Drawing 2D stuff tutorial":
This clear/draw/display cycle is the only good way to draw things. Don't try other strategies, such as keeping pixels from the previous frame, "erasing" pixels, or drawing once and calling display multiple times. You'll get strange results due to double-buffering.
Modern graphics hardware and APIs are really made for repeated clear/draw/display cycles where everything is completely refreshed at each iteration of the main loop. Don't be scared to draw 1000 sprites 60 times per second, you're far below the millions of triangles that your computer can handle.

EDIT: added the quote from the tutorial
« Last Edit: March 26, 2017, 01:07:23 am by Hapax »
Selba Ward -SFML drawables
Cheese Map -Drawable Layered Tile Map
Kairos -Timing Library
Grambol
 *Hapaxia Links*

lowarago

  • Newbie
  • *
  • Posts: 10
    • View Profile
Re: Blinking sprites, draw on click.
« Reply #2 on: March 26, 2017, 01:28:58 am »
Ok, thanks, but when I press the button again, the screen doesn't flick anymore.

Hapax

  • Hero Member
  • *****
  • Posts: 3379
  • My number of posts is shown in hexadecimal.
    • View Profile
    • Links
Re: Blinking sprites, draw on click.
« Reply #3 on: March 26, 2017, 01:48:33 pm »
It's likely that this is partly just luck.
If both buffers are identical, there will be no flickering. However, to make them both identical, you would have to update both identically, which would involve drawing and swapping twice in one frame. This is unreliable; I have not tested this theory.
There doesn't seem to be any reason to attempt this, though. As mentioned above, refreshing everything every frame is not really a problem. However, if it's because you want to only draw things once (rather than updating the window once), you can do this with a render texture. Update the render texture (you draw to it in the same way you draw to a window) whenever something changes, then draw the current render texture to the window each frame. Drawing to a render texture and then drawing that render texture to the window is a common technique as it's required for full game post effects.

I suppose the question that should be asked is:
are you having some trouble with the frame rate by drawing directly to the window every frame?
Selba Ward -SFML drawables
Cheese Map -Drawable Layered Tile Map
Kairos -Timing Library
Grambol
 *Hapaxia Links*