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

Author Topic: [SOLVED] RenderWindow::dislay() takes 80ms  (Read 2238 times)

0 Members and 1 Guest are viewing this topic.

Ullaakut

  • Newbie
  • *
  • Posts: 6
    • View Profile
[SOLVED] RenderWindow::dislay() takes 80ms
« on: June 20, 2015, 02:52:52 pm »
Hi,

I've got a performance issue: I'm working on an online graphical client which displays a map according to what the servers sends. The window has to display ~1500-2000 sprites at every frame, most of which does not change position nor texture.

The networking part takes 4µs in the loop, getting the objects from the EntitiesManager takes 35µs, drawing them takes also 4-5µs, but the call to RenderWindow::display() in the loop takes 80 000µs and therefore destroys my framerate.

What could be the reason of this problem? Too many sprites?

Here is my game loop:

// Launches the game
void GameEngine::run()
{
  while(_window.isOpen())
  {
    if (_em != nullptr && _em->isEnded())
      break;
    else if (_em != nullptr && _camera == nullptr)
      _camera = new ViewPoint(_em->getWidth(), _em->getHeight());
    sf::Event e;
    while (_window.pollEvent(e))
    {
      if (e.type == sf::Event::Closed)
        _window.close();
      if (e.type == sf::Event::MouseButtonPressed)
        selectTarget(e.mouseButton.x, e.mouseButton.y);
      if (e.type == sf::Event::KeyPressed)
        {
        if (e.key.code == sf::Keyboard::Escape)
          _window.close();
        if (e.key.code == sf::Keyboard::Left && _camera->getX() > 10)
          _camera->setPos(glm::vec2(_camera->getX() - 1, _camera->getY()));
        if (e.key.code == sf::Keyboard::Right && _camera->getX() < _em->getWidth() - 10)
          _camera->setPos(glm::vec2(_camera->getX() + 1, _camera->getY()));
        if (e.key.code == sf::Keyboard::Up && _camera->getY() > 10)
          _camera->setPos(glm::vec2(_camera->getX(), _camera->getY() - 1));
        if (e.key.code == sf::Keyboard::Down && _camera->getY() < _em->getHeight() - 10)
          _camera->setPos(glm::vec2(_camera->getX(), _camera->getY() + 1));
      }
    }
    _network->doSelect();
    if (_network->isAlive())
    {
      std::list<std::string> msg = _network->getMessages();
      for (auto it = msg.begin(); it != msg.end(); it++)
        {
          std::cout << *it << std::endl;
          if ((*it).compare("BIENVENUE") == 0)
            {
              _network->addMessage(ASK_EVERYTNG);
              std::cout << "Asking everything" << std::endl;
            }
          else
            _parser->parse(*it);
        }
    }
    else
    {
      std::cout << "Network dead" << std::endl;
      break;
    }

    // if (_camera->hasTarget())
      // _camera->updatePos();
    _window.clear();
    if (_em != nullptr && _camera != nullptr)
      drawMap();
    _window.display();
  }
  close(_server_fd);
}
 

(I know the networking/parsing part is kind of dirty but it's not the problem here :p)
« Last Edit: June 20, 2015, 08:22:21 pm by Ullaakut »

Hapax

  • Hero Member
  • *****
  • Posts: 3050
  • My number of posts is shown in hexadecimal.
    • View Profile
Re: RenderWindow::dislay() takes 80ms
« Reply #1 on: June 20, 2015, 04:14:31 pm »
Have you set a frameratelimit or turned on vsync?
What makes you think that it's .display() that is taking so long?

I don't understand your (over-)use of "this->" here. I can't see that it's necessary to use it at all in this code but it's more confusing because you're also using it in conjunction with an underscore prefixed member name.
Selba Ward - SFML drawables
Kairos - Timing Library
Rectangular Boundary Collision - Rectangular SAT Collision

@Hapaxiation - Hapaxia on Twitter

Ullaakut

  • Newbie
  • *
  • Posts: 6
    • View Profile
Re: RenderWindow::dislay() takes 80ms
« Reply #2 on: June 20, 2015, 04:29:49 pm »
I did set a frameratelimit at 60, however I did not turn on vsync.

I did use  std::chrono::steady_clock::time_point to measure the difference between each point of my game loop and I'm 100% sure that RenderWindow::display() takes 75000 to 85000 µs at every frame, thus reducing my framerate from 60 to barely 10 frames per second :/

[And yes I know I don't need this-> but when I began this project, I wasn't aware of it. I'll clean that off later]
« Last Edit: June 20, 2015, 04:31:50 pm by Ullaakut »

eXpl0it3r

  • SFML Team
  • Hero Member
  • *****
  • Posts: 10162
    • View Profile
    • development blog
    • Email
AW: RenderWindow::dislay() takes 80ms
« Reply #3 on: June 20, 2015, 06:01:49 pm »
Is your graphics driver uptodate? How does it behave with a smaller number of sprites? Did you run it in release mode?
Official FAQ: https://www.sfml-dev.org/faq.php
Nightly Builds: https://www.nightlybuilds.ch/
——————————————————————
Dev Blog: https://dev.my-gate.net/
Thor: http://www.bromeon.ch/libraries/thor/

Ullaakut

  • Newbie
  • *
  • Posts: 6
    • View Profile
Re: RenderWindow::dislay() takes 80ms
« Reply #4 on: June 20, 2015, 06:40:45 pm »
I'm having an issue when I run my program under Valgrind that seems related to my graphics driver but I also have it when I run OpenGL programs and my last OpenGL project did run smoothly without performance issue. I  didn't use SFML back then though.

This is a part of a typical valgrind report when I use OpenGL-related graphical libraries:

==1757== Invalid write of size 8
==1757==    at 0x4C2F5F3: memcpy@GLIBC_2.2.5 (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==1757==    by 0xA8069BF: ??? (in /usr/lib/dri/fglrx_dri.so)
==1757==  Address 0x7fa15b9da000 is not stack'd, malloc'd or (recently) free'd
==1757==
==1757== Invalid write of size 8
==1757==    at 0x4C2F5F3: memcpy@GLIBC_2.2.5 (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==1757==    by 0xA807019: ??? (in /usr/lib/dri/fglrx_dri.so)
==1757==    by 0x4: ???
==1757==  Address 0x7fa15b80dd00 is not stack'd, malloc'd or (recently) free'd
==1757==
==1757== Invalid write of size 8
==1757==    at 0x4C2F5F3: memcpy@GLIBC_2.2.5 (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==1757==    by 0x951F2BB: ??? (in /usr/lib/dri/fglrx_dri.so)
==1757==    by 0x7: ???
==1757==    by 0xB9C47BF: ???
==1757==    by 0x4FFFFFFFFF: ???
==1757==    by 0x100000000: ???
==1757==    by 0xBB76700: ???
==1757==    by 0xFFFFFFFFFFFFFFFE: ???
==1757==  Address 0x7fa15b7e7300 is not stack'd, malloc'd or (recently) free'd
==1757==
==1757== Invalid write of size 2
==1757==    at 0x4C2F63B: memcpy@GLIBC_2.2.5 (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==1757==    by 0x9A71E00: ??? (in /usr/lib/dri/fglrx_dri.so)
==1757==    by 0xBBB68CF: ???
==1757==    by 0xBBB50EF: ???
==1757==    by 0xBBB50EF: ???
==1757==    by 0xBBB442F: ???
==1757==    by 0xB90832F: ???
==1757==    by 0xFFEFFDF3F: ???
==1757==    by 0xFFEFFDD4F: ???
==1757==    by 0x9DAF063: ??? (in /usr/lib/dri/fglrx_dri.so)
==1757==    by 0xFFEFFE0AF: ???
==1757==    by 0xFFEFFE09F: ???
==1757==  Address 0x7fa15b7e7b00 is not stack'd, malloc'd or (recently) free'd

 



Compiling it in release mode instead of debug mode doesn't change the framerate :/

I tried using a server initialized with a 1*1 map (So only a few sprites) and the framerate doesn't change either...

eXpl0it3r

  • SFML Team
  • Hero Member
  • *****
  • Posts: 10162
    • View Profile
    • development blog
    • Email
Re: RenderWindow::dislay() takes 80ms
« Reply #5 on: June 20, 2015, 06:54:05 pm »
I tried using a server initialized with a 1*1 map (So only a few sprites) and the framerate doesn't change either...
Then I guess it's a driver issue. How do other OpenGL games perform on your system?
What's your specs anyways (incl. the driver you use)?

You could build SFML in debug mode and see what function exactly within SFML takes up all the time.
Official FAQ: https://www.sfml-dev.org/faq.php
Nightly Builds: https://www.nightlybuilds.ch/
——————————————————————
Dev Blog: https://dev.my-gate.net/
Thor: http://www.bromeon.ch/libraries/thor/

Ullaakut

  • Newbie
  • *
  • Posts: 6
    • View Profile
Re: RenderWindow::dislay() takes 80ms
« Reply #6 on: June 20, 2015, 07:11:58 pm »
I'll try it on another computer tomorrow then :- )

My previous OpenGL project, even though I had the same valgrind errors, did run normally. I have an AMD Radeon HD 8570M / i7 2.4GHz / 8gb RAM and I currently run it under Ubuntu 14.10, and the set driver is "Video driver for the AMD graphics accelerators from fglrx-updates" (I don't know more about it though)

(When I said that compiling in release mode didn't change anything, I was talking about the -g3 rule on g++ compilation of my own Makefile. I didn't try recompiling the SFML)

Jesper Juhl

  • Hero Member
  • *****
  • Posts: 1405
    • View Profile
    • Email
Re: RenderWindow::dislay() takes 80ms
« Reply #7 on: June 20, 2015, 08:03:04 pm »
-g3 just controls if debug symbols are generated or not. That doesn't matter for performance.
What you want is -O2 or -O3 to build with optimization enabled.

Ullaakut

  • Newbie
  • *
  • Posts: 6
    • View Profile
Re: RenderWindow::dislay() takes 80ms
« Reply #8 on: June 20, 2015, 08:22:10 pm »
Thank you very much Jesper, I forgot about that option and it's now going smoothly at 60 fps!

Thanks for everyone who helped me out on this one! :)

Jesper Juhl

  • Hero Member
  • *****
  • Posts: 1405
    • View Profile
    • Email
Re: RenderWindow::dislay() takes 80ms
« Reply #9 on: June 20, 2015, 11:28:49 pm »
You could build SFML in debug mode and see what function exactly within SFML takes up all the time.
Timing things in a (unoptimized) debug build is fairly pointless. What functions actually take time changes significantly once the optimizer has had its way with your code. Always time release (optimized) builds (and yes, you can build optimized with debug symbols).
« Last Edit: June 20, 2015, 11:30:41 pm by Jesper Juhl »

 

anything