Author Topic: Fractals [EGSL]  (Read 11014 times)

Bereb

  • Guest
Fractals [EGSL]
« on: November 13, 2012, 09:24:29 AM »
An example of Mandelbrot (and speed test) :
Try to comment all lines beginning with 'local' to see the difference

Code: [Select]
#!/usr/bin/egsl
------------------------------------------------------------
-- MandelBrot (nov 2012) - EGSL 1.5.3 (B.Carette)
------------------------------------------------------------
openwindow(400,300,0,"Mandelbrot (EGSL)")
backcolor(255,255,255)
clearscreen()
--setframetimer(1000)

-- constants
local width, height, minre, maxre, mini, maxi, refactor, imfactor
width, height = screenwidth(), screenheight()
minre, maxre = -2.0, 1
mini = -1.2
maxi = mini+(maxre-minre)*height/width
refactor = (maxre-minre)/(width-1)
imfactor = (maxi-mini)/(height-1)

-- variables
local st, et
local cim, cre, zre, zim, zre2, zim2
local t

--MAIN PROGRAM
st = timerticks()
for y = 0, height+16 do
cim = maxi-y*imfactor
for x = 0, width do
cre = minre+x*refactor
zre = cre
zim = cim
for i = 0, 50 do
zre2 = zre*zre
zim2 = zim*zim
if zre2 + zim2 > 4 then
color(255-(i+5), i*5, i)
dot(x,y)
break
end
zim = 2*zre*zim+cim
zre = zre2-zim2+cre
end
end
end
et =  timerticks()
t = tostring(et-st).." ms"
color(255,255,255)
drawtext(1, 10, t)
sync()

inkey()
closewindow()

--[[--
*** COMPARISONS ***

Interpreted Basic-like scripting languages :
* EGSL : +ou-  3000 ms / 600 to 800 ms (with variables as 'local')
* SDLBasic  :   3400 ms
* FBSL : +ou- 10000 ms (freestyle Basic on win32)

Compiled Basics :
* PureBasic :   1438 ms / 422 ms compiled (win32)
                     1109 ms /  78 ms compiled (win32), with 'SetGadgetState()' after 2nd 'Next'
* GFA-BAsic :    315 ms / 198 ms compiled (win32)
* FreeBASIC :    220 to 400 ms

Lua + FLTK :
* murgaLua  :   1900 to 2500 ms / 450 to 600 ms (with variables as 'local')
                 
--]]--
« Last Edit: November 20, 2012, 02:44:18 PM by Bereb »

Cybermonkey

  • Administrator
  • *****
  • Posts: 0
Re: Fractals
« Reply #1 on: November 13, 2012, 09:31:52 AM »
As for speed issues one should use redraw() instead of sync() because sync() is implemented as
Code: [Select]
wait (timeleft())
redraw()
So even if timeleft=0 there is a second function call.

Tomaaz

  • Guest
Re: Fractals
« Reply #2 on: November 13, 2012, 09:33:54 AM »
There is something similar on basicprogramming.org forum. You will find speed comparison and examples of Mandelbrot Set real time animation there.

Bereb

  • Guest
Re: Fractals
« Reply #3 on: November 13, 2012, 09:52:39 AM »
As for speed issues one should use redraw() instead of sync()
Effectively. After several tests with both redraw() and sync(), I've got an average of 587ms for redraw() and 652ms for sync().

There is something similar on basicprogramming.org forum.
Thanks for the link. I didn't know that forum, it seems to be interesting
Your Mandelbrot Set example in that forum should run faster with 'local' variables, at least 2 times faster and then EGSL should sit after BaCon and before NaaLaa  :)
I'v not tested it but I've a similar script adapted from X11-Basic. I don't know if i can post it here because of this comment at the head : Mandelbrotfraktale (c) Markus Hoffmann (copyright ?)
« Last Edit: November 13, 2012, 10:45:40 AM by Bereb »

Cybermonkey

  • Administrator
  • *****
  • Posts: 0
Re: Fractals
« Reply #4 on: November 13, 2012, 02:54:57 PM »
Hm, Markus is also registered at bp.org. (Are there any interpreter creators whose name is not Markus or Marcus? ;D) But I think if you leave the copyright message and do not change the code you might post it here.

Bereb

  • Guest
Re: Fractals
« Reply #5 on: November 13, 2012, 03:25:33 PM »
So then ...  :)
I have just changed the size of the screen and of course I have adapted the code so that it can work with EGSL

Code: [Select]
#!/usr/bin/egsl
--[[
 °
 ° Mandelbrotfraktale (c) Markus Hoffmann
 ° Simple and direct drawing algorithm.
 ° X11-Basic, adapted for EGSL
 °
--]]

local bx,by,bw,bh
local sx,sy,sw,sh
local t0, t1
local gx,gy,zx,zy,nzx
local col,r,v,b

bx=0
by=0
bw=800
bh=800

sx=-2.2
sy=-1.7
sw=3.4
sh=3.4

openwindow(bw,bh,0,"Mandel simple - EGSL (adapted from X11-Basic) -")
clearscreen()

t0=timerticks()
for x=bx,bx+bw do
for y=by,by+bh do
gx=(x-bx)/bw*sw+sx
gy=(y-by)/bh*sh+sy
zx=gx
zy=gy
for c=0,255 do
col = c
nzx=zx*zx - zy*zy + gx
zy=2*zx*zy+gy
zx=nzx
if zx*zx + zy*zy > 4 then
col = c
break
end 
end
r = col*256+col
v = col*256+col*32
b = col*256+col*64
colour(r,v,b)
dot(x,y)
end
redraw()
end
t1=timerticks()
temps = tostring((t1-t0)/1000)
color(255,255,0)
drawtext(1,1,temps.." secondes.")
redraw()

inkey()
closewindow()

about 20 sec. this way (about 48 sec. without 'local' variables)

Cybermonkey

  • Administrator
  • *****
  • Posts: 0
Re: Fractals
« Reply #6 on: November 13, 2012, 03:47:40 PM »
Wow. By the way (another annoying tipp of me), this is enough for drawtext:
Code: [Select]
temps = (t1-t0)/1000because it automatically converts numbers to strings.  ;)

My computer needs about 4 sec. with local definitions and about 15 sec. without. So, hey, thanks for your performance tipps!
 

Tomaaz

  • Guest
Re: Fractals
« Reply #7 on: November 13, 2012, 06:57:52 PM »
I've written a real time Mandelbrot Set animation and I'm really impressed!  Not as fast as compiled languages, but much faster than other scripting languages (including JavaScript)! :o

Code: [Select]
function mandelbrot()
local przelx, przely, powiekszenie, przesx, przesy, x, y, x2, y2, x3, a, b, c, z, a2, b2
przelx = 3 / 240
przely = 2 / 160
powiekszenie = 1
przesx = 14.17799995
przesy = 79.999904
repeat
przelx = 3 / (240 * powiekszenie);
przely = 2 / (160 * powiekszenie);
for x = 0, 240 do
x3 = x - 120
for y = 0, 160 do
y3 = y - 80
c, a, b, z = 0, 0, 0, 0
x2 = (przelx * (x3 + (przesx * powiekszenie))) - 2
y2 = (przely * (y3 + (przesy * powiekszenie))) - 1
while c < 255 and z < 4 do
a2 = a * a - b * b
b2 = 2 * a * b
a = a2 + x2
b = b2 + y2
z = a * a + b * b
c = c + 1
end
if c == 255 then
colour(0, 0, 0)
else
colour(255 - c, (c % 50)* 5, c)
end
dot(x, y)
end
end
if powiekszenie < 15625500000 then
powiekszenie = powiekszenie + powiekszenie * 0.05
end
redraw()
klawisz = getkey()
until klawisz == 27
end

openwindow(240, 160, 32, "Mandelbrot animation")
mandelbrot()

Bereb

  • Guest
Re: Fractals
« Reply #8 on: November 14, 2012, 04:31:12 PM »
It's really amazing (for an interpreted language)  :)

Bereb

  • Guest
Re: Fractals
« Reply #9 on: November 15, 2012, 04:23:41 PM »
I have been working on a script that I have adapted from a murgaLua script of mine, inspired by a script found in BaCon samples  ???
It's again about fractal but with a simplistic GUI.
I deliver it to you here as it is, with its possible errors and bugs :

Code: [Select]
#!/usr/bin/env egsl
-----------------------------------------------------------
-- Fractale avec GUI - EGSL 1.5.3
-- novembre 2012
-- B.Carette
-----------------------------------------------------------
--------------------------------------------------
-- Class 'Button'
--------------------------------------------------
Button = {}
button_id = 0 -- I'm not sure it is insdispensable here
function Button:new(x, y, text)
-- crée un objet si l'utilisateur n'en fournit pas / object if not provided
local obj = {}
setmetatable(obj, self)
self.__index = self
-- initialiser l'objet / inializing object
button_id = button_id + 1
obj.id = button_id
obj.x = x or 1
obj.y = y or 1
obj.text = text or ""
obj.width = #obj.text*8 + 8
obj.height = 24
obj.color = {r = 100, g = 100, b = 100}
obj.hlight = {r = 200, g = 200, b = 200}
obj.tcol = {r = 255, g = 255, b = 255}
obj.over = false
obj.callback = function() end
-- retourner l'objet
return obj
end

function Button:draw()
local col, txt
-- update
if mousezone(self.x, self.y, self.x + self.width, self.y + self.height) then
self.over = true
else
self.over = false
end
-- mouse pressed
if self.over then
col = self.hlight
if mouseb() == 1 then
color(255,0,0)
self.callback()
end
else
col = self.color
end
-- draw
color(col.r, col.g, col.b)
fillbox(self.x, self.y, self.width + self.x, self.height + self.y)
col = self.color
color(col.r+10,col.g+10,col.b+10)
box(self.x, self.y, self.width + self.x, self.height + self.y)
col = self.tcol
color(col.r,col.g,col.b)
drawtext(self.x + 4 , self.height/2 + self.y-4 , self.text)
--
redraw()
end

--------------------------------------------------
-- Constantes, variables, tableaux
--------------------------------------------------
local MaxIters = 100
local xSize =  300
local ySize = 240
local Black = -1
local Left = -2.0
local Right = 1.0
local Top = 1.1
local Bottom = -1.0

local layout = "Fractal with EGSL"
local start  = "Please wait..."
local ready  = "Ready!"

local picol = {{127,0,0},{127,0,128},{127,0,255},{127,127,0},
{127,127,127},{127,127,255},{127,255,0},{127,255,127},
{127,255,255},{255,0,0},{255,0,127},{255,0,255},
{255,127,0},{255,127,127},{255,127,255},{255,255,0}}

--------------------------------------------------
-- Interface graphique / GUI
--------------------------------------------------
openwindow(300,300, 0, "Fractale - EGSL 1.5.3")
backcolor(150, 150, 150)
clearscreen()
color(0, 0, 0)
drawtext(110, 280, layout)

-- canevas / canvas
color(255, 255, 255)
fillbox(1, 1, 298, 264)

-- boutons de commande / buttons
btn_draw  = Button:new(2, 270, "Draw")
btn_clear = Button:new(50, 270, "Clear")
btn_exit  = Button:new(255, 270, "Exit")


--------------------------------------------------
-- Gestion des évènements / managing events
--------------------------------------------------
function quit()
os.exit()
end

function clear()
-- retracer le canevas / redrawing canvas
color(255, 255, 255)
fillbox(1, 1, 299, 250)
redraw()
end

function draw()
-- effacer le texte d'attente / clearing info text
color(255, 255, 255)
fillbox(1, 240, 122, 264)
-- signaler le début du tracé / info to user
color(255, 0, 0)
drawtext(1, 255, start)
redraw()
-- calcul / computing
for y = 0, ySize do
for x = 0, xSize do
local zr, zi = 0, 0
local cr = Left + x * (Right - Left) / xSize
            local ci = Top + y * (Bottom - Top) / ySize
            local rsquared = zr * zr
            local isquared = zi * zi
local count = 0
            while (rsquared + isquared) < 2.0 and count < MaxIters do
                zi = zr * zi * 2
                zi = zi + ci
                zr = rsquared - isquared
                zr = zr + cr
                rsquared = zr * zr
                isquared = zi * zi
                count = count+1
            end
local sum = rsquared + isquared
            if sum < 1 then
if sum < 2 then
ind = math.ceil(sum * 16)
else
ind = 16
end
color(picol[ind][1],picol[ind][2],picol[ind][3])
dot(x, y)

end --if
        end --for x
    end --for y
    -- effacer le texte d'attente / clear info text
    color(255, 255, 255)
    fillbox(1, 240, 122, 264)
    -- signaler que l'on est prêt à tracer / tell drawing is ready
    color(0, 0, 255)
    drawtext(1, 255, ready)
end

--------------------------------------------------
-- Evènements / events
--------------------------------------------------
btn_draw.callback = draw
btn_clear.callback = clear
btn_exit.callback = quit

--------------------------------------------------
-- Boucle principale / main loop
--------------------------------------------------
repeat
key = getkey()
btn_draw:draw()
btn_clear:draw()
btn_exit:draw()
until key == 27

closewindow()
8)
« Last Edit: November 15, 2012, 04:30:17 PM by Bereb »

Tomaaz

  • Guest
Re: Fractals
« Reply #10 on: November 15, 2012, 04:53:34 PM »
I've started many topics about fractals and written many examples in different languages (Yabasic, FreeBASIC, NaaLaa, BaCon, Blassic, AurelBasic), because I simply love fractals. But I think that folks here are bored of this stuff. Don't get me wrong. I have nothing against your examples. Just don't be surprised and disappointed if no one ever replies. Remember that EGSL is meant for games. ;)

Regards! :)

Cybermonkey

  • Administrator
  • *****
  • Posts: 0
Re: Fractals
« Reply #11 on: November 15, 2012, 05:05:18 PM »
Very nice. But please don't forget the closewindow in your function quit:
Code: [Select]
function quit()
        closewindow()
os.exit()
end           

Bereb

  • Guest
Re: Fractals
« Reply #12 on: November 15, 2012, 07:15:14 PM »
@Tomaaz
Yes, I remarked that EGSL was above all meant for games. That's why I was hesitating to join this forum recently, although I use EGSL since several months. I hesitate to post my scripts every time for the same reason. Moreover I'm not really a game fan. The kind of games that I appreciate is, for instance, Bubble Chain or similar.  :-\

IMHO I don't think EGSL should be limited only for games. I think it can be a good language to become initiated into programing and other stuffs, thanks to its simplicity, its performances (probably due to Lua and Pascal) and thanks to the fact it develops mainly graphics. What allows to get a quick feedback of what we put on our scripts, as Logo and Basic did in the past. I come from there (Logo, Basic, etc. on a Commodore 64 in the '80s), sorry, but I'm not at all nostalgic. World moves forward ...  :)

I don't post my scripts with the only intention of receiving congratulations or some gratefulness. In the other hand, I appreciate if one corrects my errors. I just wanted to share my modest experiments, which could be usefull, well I hope so. ???
I have an indigestion of fractals too. I use them for testing and I tested many languages this way (May be I'm an obsessive test man)  ;)
In my last script, fractal was just pretext to test my extremely naive and simplistic attempt to create command buttons with EGSL, without calling complex external libraries. However, about that, I did not feel like doing another topic, for fear that I appear to be coming to the fore  :-[

@Cybermonkey
When I put only closewindow() in my function quit(), I get this message (if a console is opened, e.g. in Geany editor) : Error: No graphics window initialized. and nothing with os.exit().
But I did not test with both : closewindow() and os.exit(). That works fine and it's  more satisfying.
Thanks

« Last Edit: November 15, 2012, 07:19:33 PM by Bereb »

Tomaaz

  • Guest
Re: Fractals
« Reply #13 on: November 15, 2012, 08:24:28 PM »
Moreover I'm not really a game fan.

Me, too. ;) All I can play is "Boulder Dash" and space shooters.  :)

IMHO I don't think EGSL should be limited only for games.

I couldn't agree more! :) Do you know that first name of the interpreter was Easy Graphic Scripting with Lua? Later Markus has changed it to Game, probably for marketing reasons.

I don't post my scripts with the only intention of receiving congratulations or some gratefulness. In the other hand, I appreciate if one corrects my errors.

I even like when people say that my work is really bad. But sometimes they just don't reply and that's what I meant. What I wanted to say was: Keep posting and don't care if there is no reply. ;)

I have an indigestion of fractals too. I use them for testing and I tested many languages this way...

Me, too. :) Here you can find my Mandelbrot Set explorer in JavaScript.

BTW Do you like coding demos? What do you thing about this one?

Regards! :)

Bereb

  • Guest
Re: Fractals
« Reply #14 on: November 16, 2012, 10:29:10 AM »
I couldn't agree more! :) Do you know that first name of the interpreter was Easy Graphic Scripting with Lua? Later Markus has changed it to Game, probably for marketing reasons.
Then my subconscious have replaced 'game' by 'graphic'  ;D
Yes, "game" seems less austere than "graphic" or "graphic arts". But after all, games depends a lot on graphics, so we can be content with that  :)

Quote
BTW Do you like coding demos? What do you thing about this one?
Well, I had already downloaded it and I find it's a good (and amazing) presentation, which places EGSL precisely between 'game' and 'graphics'  ::)

Quote
I even like when people say that my work is really bad. But sometimes they just don't reply and that's what I meant. What I wanted to say was: Keep posting and don't care if there is no reply. ;)
While posting my sketchy scripts, my first intention was to return what I had taken from the experience of the other members. I learnt a lot from the former forum (which was impossible to join). The least I could do as thanks was this modest return. Afterwards everyone can do as he wants with that  :)

Thanks for the link to your Javascript demos. I don't know very well Java and Javascript, although I gave Processing a little try. But the latter seems to me rather 'heavy' and I'm looking for lighter solutions (with good performances nevertheless) like  SDLBasic or EGSL preferably (because of Lua and its better maintenance)