Turing Eliminate Flickering
From Compsci.ca Wiki
Well here goes, I saw the tutorial in the Turing Walkthrough for this and well... it didnt really explain much, so I'm going to try to give you a tutorial on what I know about View.Set and View.Update. :D
Contents |
The Basics
View.Set (alternately known as setscreen, but for the purposes of this tutorial we will be using View.Set) is a command that allows you to play around with your output screen. It allows you to change the size of the screen, the position of the screen, and other goodies that I will show you.
To Start
To start with we need to know how to use View.Set. View.Set is called on its own line and can accept many different things, here is an example:
Turing:
View.Set("graphics:500;300,position:center;center,nobuttonbar,title:View.Set tut")
now some of you are probably going, "Whoa, what the heck happened there?", well let me explain. When giving View.Set a parameter, anything that's passed is in quotations. Now lets take apart my line piece by piece:
1) View.Set : calls the Set procedure in the View module
2) ("") : the parameter passed to the Set procedure which is in quotes
3) ("graphics" : this is a screen "[b]mode[/b]" by default the screen is set to "[b]text[/b]" mode, in which the screen is measured by [b]row[/b]s and [b]column[/b]s of characters, whereas in "[b]graphics[/b]" mode, the screen is measured in pixels and use a regular cartesian plane.
4):500;300 : this sets the screen size to being 500 pixels wide(x-axis) and 300 pixels high (y-axis) in this way we can control the size of our screen to whatever we want
5)"position:center;center" : this accesses your monitor size and places your run window in the center of the screen, you can also have
Turing:
View.Set("graphics:500;300,position:0,0,nobuttonbar")
where the position of the bottom left corner of your run window would be in the bottom left-hand corner of the monitor
6)"nobuttonbar" : this is just one of a few things you can do to change the cursor, run window, and output. the following other commands can go into there as well if you so choose, seperated by a comma (,) from other commands:
nobuttonbar : this eliminates the "button bar" at the top of the run window (the one with stop, pause, print etc on it)
noecho : causes typed text not to show up on the screen
nocursor : causes the annoying Turing cursor to disappear, poof!
7)"title: View.Set tut") : changes the name on your run window from your program name run window to that of whatever follows the colon after title (eg. if your program's name is foo, the run window name would be foo run window unless changed with View.Set)
Using View.Set to eliminate Flickering
Now I've noticed a lot of people lately have taken to asking how to reduce the flickering in their programs. So I am going to do my best to explain how to stop the flickering.
To stop the flickering in programs Turing has a wonderful command called View.Update (there is also View.UpdateArea offscreenonly
But what is so special about offscreenonly you say? What it does is create an off screen buffer where all changes made to the screen are made there, and is drawn to the screen when View.Update is called. This is called double buffering. This reduces the flickering because all of the changes that you make are being made to the screen at once, so instead of seeing a clear screen for a split second then animation, then a clear screen for a split second... etc, you see all changes at once, resulting in a "smooth" animation :D
Here I have an example of using offscreenonly without View.Update and with View.Update (its just a ball bouncing)
without View.Update
Turing:
View.Set ("graphics,offscreenonly") var x, y, xChange, yChange : int := 1 const RADIUS : int := 5 Draw.Box (0, 0, maxx, maxy, black) x := maxx div 2 y := maxy div 2 loop Draw.Cls Draw.Box (0, 0, maxx, maxy, black) Draw.FillOval (x, y, RADIUS, RADIUS, green) Time.Delay (5) x += xChange y += yChange if View.WhatDotColor (x, y + RADIUS) = black then yChange *= -1 elsif View.WhatDotColor (x, y - RADIUS) = black then yChange *= -1 end if if View.WhatDotColor (x + RADIUS, y) = black then xChange *= -1 elsif View.WhatDotColor (x - RADIUS, y) = black then xChange *= -1 end if end loop
Copy and paste that code into Turing and you'll see nothing appears to happen, that's because offscreenonly mode is in effect and you are not drawing what was put to the off screen buffer using View.Update, to solve that problem just stick in a View.Update and... Voila! It should also be noted that as few View.Updates should be used as possible to avoid unnecessary slowdowns and multiple View.Updates can cause a problem
Turing:
View.Set ("graphics,offscreenonly") var x, y, xChange, yChange : int := 1 const RADIUS : int := 5 Draw.Box (0, 0, maxx, maxy, black) x := maxx div 2 y := maxy div 2 loop Draw.Cls Draw.Box (0, 0, maxx, maxy, black) Draw.FillOval (x, y, RADIUS, RADIUS, green) View.Update Time.Delay (5) x += xChange y += yChange if View.WhatDotColor (x, y + RADIUS) = black then yChange *= -1 elsif View.WhatDotColor (x, y - RADIUS) = black then yChange *= -1 end if if View.WhatDotColor (x + RADIUS, y) = black then xChange *= -1 elsif View.WhatDotColor (x - RADIUS, y) = black then xChange *= -1 end if end loop
pop that into your editor and you'll notice a ball moving around... without flickering!! yay we've solved the problem of flickering.
now a program similiar to that but WITHOUT View.Update
Turing:
View.Set ("graphics") var x, y, xChange, yChange : int := 1 const RADIUS : int := 5 Draw.Box (0, 0, maxx, maxy, black) x := maxx div 2 y := maxy div 2 loop Draw.Cls Draw.Box (0, 0, maxx, maxy, black) Draw.FillOval (x, y, RADIUS, RADIUS, green) Time.Delay (5) x += xChange y += yChange if View.WhatDotColor (x, y + RADIUS) = black then yChange *= -1 elsif View.WhatDotColor (x, y - RADIUS) = black then yChange *= -1 end if if View.WhatDotColor (x + RADIUS, y) = black then xChange *= -1 elsif View.WhatDotColor (x - RADIUS, y) = black then xChange *= -1 end if end loop
notice how flashy/flickery the screen is? that is because all changes are being made to the screen as they happen instead of all happening at once from the buffer
However, using View.Update has its drawbacks. It slows down your program IMMENSELY due to the fact that it has to update the entire screen from the buffer. The easiest way to solve this is to use a neat little command called...
View.UpdateArea
The only main difference from View.Update is that it only updates a specific area (specified by you). An example of its use is as follows:
Turing:
View.Set("offscreenonly") View.UpdateArea(0,0,100,100)
As you can see View.UpdateArea requires the screen to be in offscreenonly mode as well, but it also requires four(4) parameters (x1,y1,x2,y2), these parameters tell the computer to update the area within these boundaries and thus it can speed up your program (as its not updating the entire screen like View.Update)
An example of View.UpdateArea in action (our ball program)
Turing:
View.Set ("graphics,offscreenonly") var x, y, xChange, yChange : int := 1 const RADIUS : int := 5 Draw.Box (0, 0, maxx, maxy, black) x := maxx div 2 y := maxy div 2 loop Draw.Cls Draw.Box (0, 0, maxx, maxy, black) Draw.FillOval (x, y, RADIUS, RADIUS, green) View.UpdateArea (x - 10, y - 10, x + 10, y + 10) Time.Delay (5) x += xChange y += yChange if View.WhatDotColor (x, y + RADIUS) = black then yChange *= -1 elsif View.WhatDotColor (x, y - RADIUS) = black then yChange *= -1 end if if View.WhatDotColor (x + RADIUS, y) = black then xChange *= -1 elsif View.WhatDotColor (x - RADIUS, y) = black then xChange *= -1 end if end loop
as you can see the program runs faster now that the buffer isnt entirely being transferred to the screen.
Also, if for any reason you want to turn offscreenonly off, simply create another call to View.Set with nooffscreenonly in it to deactivate offscreen only. Another note is that, by default, your programs begin in nooffscreenonly mode.
noofscreenonly in action:
Turing:
View.Set("offscreenonly") %oops i dont want it on anymore View.Set ("nooffscreenonly")
And with that I will end my Tutorial on View.Set and View.Update(Area) and leave you to try out this newfound idea :D hope this helps you animators out there!!