April 25, 2019, 04:19:09 AM

Author Topic: About Graphic buffer Flipping  (Read 291 times)

Offline wookie22

  • Jr. Member
  • **
  • Posts: 22
    • Hidden Deep
About Graphic buffer Flipping
« on: March 17, 2019, 11:41:54 AM »
Bmx help states that "Flip swap the front and back buffers of the current graphics objects".

So if I have some movement in program logic achieved by drawing new object position to back buffer and then flipping buffers and then I do this:

if KeyDown(KEY_SPACE)
   While 1
      Flip 1
   Wend
Endif

So when I press space I should see my movement going back and forward in a loop right? So why I just see still frame?
Hidden Deep - 2D Action & Exploration Sci-Fi Thriller for PC/Mac/Linux
http://www.hiddendeepgame.com

Offline Derron

  • Hero Member
  • *****
  • Posts: 1953
Re: About Graphic buffer Flipping
« Reply #1 on: March 17, 2019, 12:07:07 PM »
Nope.

Flip: bring to the screen what you drew before

DrawImage XYZ 'not yet on screen
DrawImage XYZ2 'not yet on screen
DrawText bla 'not on screen
flip 'now xyz, xyz2 and bla are on screen

flip 'whatever is on the backbuffer is shovled to the screen - garbage or the same stuff as above, no guarantee

Your while loop is running forever - so you only put your drawn stuff on the screen during the first "flip" and all follow up flips are... sending "whatever is there" to the screen.
You cannot guarantee that this is your drawn stuff - might as well be some "random memory". Just do some "alt-tab" while it runs, open some applications - you will see how parts of your screen wander into your application canvas/screen.


bye
Ron

Offline Matty

  • Hero Member
  • *****
  • Posts: 629
    • MattiesGames
Re: About Graphic buffer Flipping
« Reply #2 on: March 17, 2019, 06:34:31 PM »
Flip actually copies the back buffer to the front buffer so they are identical after flipping.  Yes the word swap does indeed sound like they are exchanged not copied.  Bad wording. 

Offline Yellownakji

  • Full Member
  • ***
  • Posts: 171
  • Whoop-de-doo-ba-dooo!
Re: About Graphic buffer Flipping
« Reply #3 on: March 17, 2019, 09:00:47 PM »
Bmx help states that "Flip swap the front and back buffers of the current graphics objects".

So if I have some movement in program logic achieved by drawing new object position to back buffer and then flipping buffers and then I do this:

if KeyDown(KEY_SPACE)
   While 1
      Flip 1
   Wend
Endif

So when I press space I should see my movement going back and forward in a loop right? So why I just see still frame?


You only use flip at the end of your application loop.

Code: [Select]
graphics(640,460,60,GRAPHICS_BACKBUFFER) 'Set graphics; using backbuffer is recommended.  60 = hertz.   writing 60 fixes to 60 so it's better to detect.

While not app_terminate() 'App_terminate can be a user variable too; whatever you use to keep the game running
     cls 'clear the screen
          '---------------------------------
          'do your app crap here
          '---------------------------------
     flip 'see flip document for vsync support
wend

Offline TomToad

  • Sr. Member
  • ****
  • Posts: 371
Re: About Graphic buffer Flipping
« Reply #4 on: March 18, 2019, 10:00:13 AM »
Flip actually copies the back buffer to the front buffer so they are identical after flipping.  Yes the word swap does indeed sound like they are exchanged not copied.  Bad wording.

This is not quite true.  When the graphics context is in window mode, then the back buffer is copied to the front buffer, but when in fullscreen mode, the buffers are actually swapped.  Try this example program.  Comment and uncomment the various lines to see the effect.  The program first draws a square, flips, then draws a circle without clearing the screen.  If the back buffer is copied, then you should see both square and circle on the screen (which it does when windowed).  When full screen, only the circle appears.  You can press SPACE to flip again without drawing or clearing the buffers, what happens depends on the video card and graphics driver used.  On my computer, DX7 and OpenGL flips between the square and the circle.  On DX9, the square gets cleared by the driver for some reason, so it flips between the circle and a blank screen.
Code: [Select]
SuperStrict
SetGraphicsDriver GLMax2DDriver()
'SetGraphicsDriver D3D9Max2DDriver()
'SetGraphicsDriver D3D7Max2DDriver()

'Graphics 800,600 'Windowed mode
Graphics 800,600,32 'Fullscreen mode

Cls
DrawRect 10,10,100,100
Flip
DrawOval 120,10,100,100
Flip

While Not KeyHit(KEY_ESCAPE) And Not AppTerminate()
If KeyHit(KEY_SPACE) Then Flip
Wend

------------------------------------------------
8 rabbits equals 1 rabbyte.

Offline wookie22

  • Jr. Member
  • **
  • Posts: 22
    • Hidden Deep
Re: About Graphic buffer Flipping
« Reply #5 on: March 18, 2019, 01:15:42 PM »
TomToad - yes, that is what I was expecting and didn't happened - I've just forgot to try it on fullscreen :)

My game logic is 60Hz and Graphics mode is 120Hz. So I want just wait two v-syncs instead of one so. How do I wait for another V-sync without buffer flipping?
Hidden Deep - 2D Action & Exploration Sci-Fi Thriller for PC/Mac/Linux
http://www.hiddendeepgame.com

Offline Derron

  • Hero Member
  • *****
  • Posts: 1953
Re: About Graphic buffer Flipping
« Reply #6 on: March 18, 2019, 02:35:11 PM »
Just do nothing every second frame on 120hz - no cls, no drawimage, no flip.
or just delay properly.


But who cares what hz that screen has?
run your logic with X hertz
render when the screen refresh desires (vsync).

loop
 updateIfNeeded 'fixed rate logic
 renderAndFlipIfNeeded
 delay(time left to still satisfy update and render needs)
endloop


Have a look at this:
https://github.com/GWRon/Dig/blob/master/base.util.deltatimer.bmx
-> Method Loop

To see it in action:
https://github.com/GWRon/Dig/blob/master/samples/graphicalapp/graphicalapp.bmx

basically you connect some update and render function (in which you do your stuff) and it takes care of the stuff you need.


bye
Ron

Offline wookie22

  • Jr. Member
  • **
  • Posts: 22
    • Hidden Deep
Re: About Graphic buffer Flipping
« Reply #7 on: March 18, 2019, 02:49:04 PM »
About that Delay - is it precise enough for that? It measures time in whole milliseconds while single refresh has also fraction part (like 16.667 @60Hz)
Hidden Deep - 2D Action & Exploration Sci-Fi Thriller for PC/Mac/Linux
http://www.hiddendeepgame.com

Offline TomToad

  • Sr. Member
  • ****
  • Posts: 371
Re: About Graphic buffer Flipping
« Reply #8 on: March 18, 2019, 03:48:50 PM »
Here is one method for fixing the logic rate.  By changing the Flip to Flip False, you can show that the logic runs the same speed even when the machine is running much faster.
Code: BlitzMax
  1. 'Fixed logic rate demo
  2. 'by TomToad
  3. 'March 18,2019
  4. '
  5. 'This program works by creating a timer to run at 60 htz
  6. '  TimerTicks() will return the number of ticks since the
  7. '  timer was created.  By subtracting the last count from
  8. '  the curent, we can find out how many ticks have occured
  9. '  and therefor the number of times the logic loop needs
  10. '  to run.
  11. '  on a system running at exactly 60 htz, TimerCount will
  12. '  always equal 1.  If the system is runnung faster than
  13. '  60 htz, then sometimes TimerCount will equal 1 and
  14. '  sometimes 0, causing the last frame to be duplicated.
  15. '  if the system is running slower, then TimerCount will
  16. '  sometimes be larger than 1, causing the logic to be
  17. '  run more than once, some frames will be skipped, but
  18. '  overall speed and physics simulation will still be the
  19. '  same.
  20. SuperStrict
  21.  
  22. Graphics 800,600,32
  23. Local Timer:TTimer = CreateTimer(60)
  24. Local TimerLast:Int = 0
  25. Local TimerCount:Int, TimerCurrent:Int
  26. Local x:Float = 0.0
  27. Local y:Float = 300.0
  28.  
  29. 'some stuff for calculating frames per second
  30. Local LogicFPS:Int, LogicFrameCount:Int, RenderFPS:Int, RenderFrameCount:Int, NextTime:Int
  31. NextTime = MilliSecs() + 1000
  32.  
  33.  
  34. While Not KeyHit(KEY_ESCAPE) And Not AppTerminate()
  35.  
  36.         'logic portion of the game runs 60 times a second
  37.         TimerCurrent = TimerTicks(Timer)
  38.         TimerCount = TimerCurrent-TimerLast
  39.         TimerLast = TimerCurrent
  40.        
  41.         For Local t:Int = 1 To TimerCount
  42.                 x :+ 1.0
  43.                 If x > 800.0 Then x = 0.0
  44.                 LogicFrameCount :+ 1
  45.         Next
  46.        
  47.         'render part of the game
  48.         Cls
  49.         DrawOval x-10,y-10,20,20
  50.         DrawText "Render speed = "+RenderFPS+" FPS",10,10
  51.         DrawText "Logic speed = "+LogicFPS+" FPS",10,30
  52.         Flip 'Change to Flip False to have the demo run as fast as possible
  53.         RenderFrameCount :+ 1
  54.        
  55.         If MilliSecs() >= NextTime
  56.                 NextTime :+ 1000
  57.                 LogicFPS = LogicFrameCount
  58.                 LogicFrameCount = 0
  59.                 RenderFPS = RenderFrameCount
  60.                 RenderFrameCount = 0
  61.         EndIf
  62. Wend
  63.  
------------------------------------------------
8 rabbits equals 1 rabbyte.

Offline wookie22

  • Jr. Member
  • **
  • Posts: 22
    • Hidden Deep
Re: About Graphic buffer Flipping
« Reply #9 on: March 18, 2019, 04:00:00 PM »
I think that when you get rid of waiting for V-Sync then there is tearing risk. I need to test it
Hidden Deep - 2D Action & Exploration Sci-Fi Thriller for PC/Mac/Linux
http://www.hiddendeepgame.com

Offline Derron

  • Hero Member
  • *****
  • Posts: 1953
Re: About Graphic buffer Flipping
« Reply #10 on: March 18, 2019, 04:16:11 PM »
Of course you can wait for vsync - and if you calculate that time you can at least have a slight "delay" (if you want) as this releases some stress of the cpu (if possible).


bye
Ron

Offline imaginaryhuman

  • Jr. Member
  • **
  • Posts: 7
Re: About Graphic buffer Flipping
« Reply #11 on: March 29, 2019, 11:20:54 PM »
You'd think that it would be better to render to texture and then, when done, render that texture to the front buffer. ie replace the flip with a render-texture output to the visible screen. The you also get the benefit of being able to run  shader on the rendering of the render-texture to the screen (to do warping, coloring and effects etc).

Offline Steve Elliott

  • Hero Member
  • *****
  • Posts: 1719
Re: About Graphic buffer Flipping
« Reply #12 on: March 30, 2019, 08:39:36 AM »
Quote
Here is one method for fixing the logic rate...

Thanks for sharing that Tom.
Windows 10, 64-bit, 16Gb RAM, CPU Intel i5, 3.2 GHz, Nvidia GeForce GTX 1050 (2Gb).
MacOS Mojave, 64-bit, 8Gb RAM, CPU Intel i5, 2.3 Ghz, Intel Iris Plus Graphics 640 1536 MB.
Linux Mint 19.1, 64-bit, 16Gb RAM, CPU Intel i5, 3.2 GHz, Nvidia GeForce GTX 1050 (2Gb).

Offline Derron

  • Hero Member
  • *****
  • Posts: 1953
Re: About Graphic buffer Flipping
« Reply #13 on: March 30, 2019, 08:57:54 AM »
My deltatimer-type allows to limit FPS too - sometimes you do not need 60fps. So in some "calm games" you might come along with 30fps - no need to stress Old Aunt Lizzys AMD duron with 60 fps ;-)


@ imaginaryhuman
Feel free to post some samples. So we might merge that stuff with Col's Render2Texture (DX+GL
https://github.com/davecamp/Render2Texture

Or does this - compared to Col's work with NG's SDL.mod already?


bye
Ron