Author Topic: Fast filled circles routine  (Read 5335 times)

0 Members and 1 Guest are viewing this topic.

Offline MacBernick

  • LV3 Member (Next: 100)
  • ***
  • Posts: 93
  • Rating: +3/-0
    • View Profile
Fast filled circles routine
« on: January 15, 2014, 09:18:39 am »
After a discussion an another thread about filled circles, I made a little program using FILLPOLY_P to simulate a fillled circle. It was really slow because of the use of a FOR loop to make a list of coordinates to feed the FILLPOLY function. One day Han told me it would be more efficient to call MAKELIST for building lists, so I modified it a bit, and this is now REALLY faster :)

You can push the attached program in your calc or the simulator, run "circles" for a quick demo drawing random circles on screen at a nice speed, or use the EXPORTed FILLCIRCLE_P(centerX, centerY, radius, color) function in your program.

You can also copy/past the function in your program if you want to use it but don't want to rely on an external lib.

NB : these are not perfect circles, they are not suitable for mathematics purposes. Also, very small circle may look weird.

Enjoy
« Last Edit: January 15, 2014, 09:21:08 am by MacBernick »

Offline Han

  • LV3 Member (Next: 100)
  • ***
  • Posts: 62
  • Rating: +7/-0
    • View Profile
Re: Fast filled circles routine
« Reply #1 on: January 15, 2014, 09:56:33 am »
I have even gone as far as replacing loops with either a makelist or makemat (double loop) even if I'm not generating lists or matrices. Simply create a procedural function that returns garbage data and don't store the resulting list or matrix. Have the procedural function do what you would normally do in a loop.
Code: [Select]
mainprogram()
begin
  makemat(prg(I,J),25,25);
end;

prg(x,y)
begin
  // code that loops x from 1 to 25 and y from 1 to 25 goes here
  return(0);
end;

I don't remember if the speed difference is still significant ever since the most recent firmware (never retested).

Offline bb010g

  • LV6 Super Member (Next: 500)
  • ******
  • Posts: 427
  • Rating: +22/-1
  • I do stuff
    • View Profile
    • elsewhere on the net
Re: Fast filled circles routine
« Reply #2 on: January 15, 2014, 10:00:23 am »
If they just throw away the outputs as they go instead of making a list and throwing it away, then that's nice; we just got speedy effectual mapping.
Arch Linux user
Haskell newbie | Warming up to Lua | Being dragged into C++
Calculators: HP 35s, Casio Prizm, TI-Nspire CX CAS, HP-28s, HP Prime, Mathematica 9 (if that counts)
π: 3.14...; l: 108; i: 105; e: 101; l+i+e: 314
THE CAKE IS A LIE IS A PIE

Offline MacBernick

  • LV3 Member (Next: 100)
  • ***
  • Posts: 93
  • Rating: +3/-0
    • View Profile
Re: Fast filled circles routine
« Reply #3 on: January 15, 2014, 10:02:49 am »
Yeah that's clever. FOR loops deprecated ? ^^

Offline DJ Omnimaga

  • Now active at https://codewalr.us
  • CoT Emeritus
  • LV15 Omnimagician (Next: --)
  • *
  • Posts: 55821
  • Rating: +3151/-232
  • CodeWalrus founder & retired Omnimaga founder
    • View Profile
    • DJ Omnimaga Music
Re: Fast filled circles routine
« Reply #4 on: January 15, 2014, 06:56:08 pm »
Very good work :D
In case you are wondering where I went, I left Omni back in 2015 to form CodeWalrus due to various reasons explained back then, but I stopped calc dev in 2016 and am now mostly active on the CW Discord server at https://discord.gg/cuZcfcF


Bandcamp|Reverbnation|Facebook|Youtube|Twitter

Offline bb010g

  • LV6 Super Member (Next: 500)
  • ******
  • Posts: 427
  • Rating: +22/-1
  • I do stuff
    • View Profile
    • elsewhere on the net
Re: Fast filled circles routine
« Reply #5 on: January 15, 2014, 09:43:17 pm »
Actually, couldn't you just do
Code: [Select]
mainprogram()
begin
  makemat(
    // code that loops x from 1 to 25 and y from 1 to 25 goes here
    return(0);
  ,25,25);
end;
if the code was short enough?
Arch Linux user
Haskell newbie | Warming up to Lua | Being dragged into C++
Calculators: HP 35s, Casio Prizm, TI-Nspire CX CAS, HP-28s, HP Prime, Mathematica 9 (if that counts)
π: 3.14...; l: 108; i: 105; e: 101; l+i+e: 314
THE CAKE IS A LIE IS A PIE

Offline MacBernick

  • LV3 Member (Next: 100)
  • ***
  • Posts: 93
  • Rating: +3/-0
    • View Profile
Re: Fast filled circles routine
« Reply #6 on: January 15, 2014, 10:01:26 pm »
I'm not sure MAKEMAT would support multiple statements. Did you try it ?

I replaced the two FOR loops in render routine in Trailblazer by a MAKEELIST, that's about 3 or 4 FPS earned.

If I got it right, only a Home variable can be used with MAKELIST ?

Offline Han

  • LV3 Member (Next: 100)
  • ***
  • Posts: 62
  • Rating: +7/-0
    • View Profile
Re: Fast filled circles routine
« Reply #7 on: January 15, 2014, 10:15:17 pm »
Actually, couldn't you just do
Code: [Select]
mainprogram()
begin
  makemat(
    // code that loops x from 1 to 25 and y from 1 to 25 goes here
    return(0);
  ,25,25);
end;
if the code was short enough?

Not really. They only way it could be short enough is if it were a single "command" (i.e. built-in command or procedural function created either in the same source file or made available via export). If your code requires more than a single semicolon, then I am pretty sure it won't work (though I never tried myself) because the arguments of makelist or makemat must be comma-separated.

Offline bb010g

  • LV6 Super Member (Next: 500)
  • ******
  • Posts: 427
  • Rating: +22/-1
  • I do stuff
    • View Profile
    • elsewhere on the net
Re: Fast filled circles routine
« Reply #8 on: January 15, 2014, 11:34:34 pm »
Han: Confirmed; from Home 'MAKEMAT(PRINT(I); PRINT(J); RETURN 0,25,25)' fails syntax checking with the cursor positioned right before the first ";". Also, I've had problems with 'MAKELIST(MAKELIST(X,X,1,10),X,1,10)' passing the syntax check but presently failing with 'Error: Bad argument type'.
Arch Linux user
Haskell newbie | Warming up to Lua | Being dragged into C++
Calculators: HP 35s, Casio Prizm, TI-Nspire CX CAS, HP-28s, HP Prime, Mathematica 9 (if that counts)
π: 3.14...; l: 108; i: 105; e: 101; l+i+e: 314
THE CAKE IS A LIE IS A PIE

Offline DJ Omnimaga

  • Now active at https://codewalr.us
  • CoT Emeritus
  • LV15 Omnimagician (Next: --)
  • *
  • Posts: 55821
  • Rating: +3151/-232
  • CodeWalrus founder & retired Omnimaga founder
    • View Profile
    • DJ Omnimaga Music
Re: Fast filled circles routine
« Reply #9 on: June 16, 2014, 12:23:35 am »
Necrobump:

Thanks to this routine, we can actually do circle-based fade-in/out animations, like in Zelda, in addition to stuff like dark cavern/dungeon effects! :D




The edited code by MacBernick looks like this:

Code: [Select]
FILLCIRCLE_P(cx, cy, r, color);

EXPORT circles()
BEGIN
DIMGROB_P(G1,320,240);
DIMGROB_P(G2,320,240);
DIMGROB_P(G3,320,240);
BLIT_P(G1,G0);
FOR A FROM 220 DOWNTO 0 DO
      RECT_P(G2,#000000);
      FILLCIRCLE_P(160, 120, A, #FF00FF);
BLIT_P(G3,G1);
BLIT_P(G3,0,0,320,240,G2,0,0,320,240,#FF00FF);
BLIT_P(G3);
END;
END;



EXPORT FILLCIRCLE_P(cx, cy, r, color)
BEGIN
   LOCAL s, cl := {}, angle := HAngle;
   HAngle := 1;

   LOCAL cl :=
      MAKELIST({EVAL(r * COS(S) + cx), EVAL(r * SIN(S) + cy)},
         S, 0, 359, 10);

   HAngle := angle;
   FILLPOLY_P(G2,cl, #FF00FF,255);
END;


You need multiple GROBs or at least a GROB large enough for each frame, because it involves transparency.
« Last Edit: June 16, 2014, 12:25:11 am by DJ Omnimaga »
In case you are wondering where I went, I left Omni back in 2015 to form CodeWalrus due to various reasons explained back then, but I stopped calc dev in 2016 and am now mostly active on the CW Discord server at https://discord.gg/cuZcfcF


Bandcamp|Reverbnation|Facebook|Youtube|Twitter

Offline bb010g

  • LV6 Super Member (Next: 500)
  • ******
  • Posts: 427
  • Rating: +22/-1
  • I do stuff
    • View Profile
    • elsewhere on the net
Re: Fast filled circles routine
« Reply #10 on: June 16, 2014, 01:22:35 am »
Necrobump:

Thanks to this routine, we can actually do circle-based fade-in/out animations, like in Zelda, in addition to stuff like dark cavern/dungeon effects! :D




The edited code by MacBernick looks like this:

Code: [Select]
FILLCIRCLE_P(cx, cy, r, color);

EXPORT circles()
BEGIN
DIMGROB_P(G1,320,240);
DIMGROB_P(G2,320,240);
DIMGROB_P(G3,320,240);
BLIT_P(G1,G0);
FOR A FROM 220 DOWNTO 0 DO
      RECT_P(G2,#000000);
      FILLCIRCLE_P(160, 120, A, #FF00FF);
BLIT_P(G3,G1);
BLIT_P(G3,0,0,320,240,G2,0,0,320,240,#FF00FF);
BLIT_P(G3);
END;
END;



EXPORT FILLCIRCLE_P(cx, cy, r, color)
BEGIN
   LOCAL s, cl := {}, angle := HAngle;
   HAngle := 1;

   LOCAL cl :=
      MAKELIST({EVAL(r * COS(S) + cx), EVAL(r * SIN(S) + cy)},
         S, 0, 359, 10);

   HAngle := angle;
   FILLPOLY_P(G2,cl, #FF00FF,255);
END;


You need multiple GROBs or at least a GROB large enough for each frame, because it involves transparency.
Why the EVALs? Also, angle should be a pragma.
Arch Linux user
Haskell newbie | Warming up to Lua | Being dragged into C++
Calculators: HP 35s, Casio Prizm, TI-Nspire CX CAS, HP-28s, HP Prime, Mathematica 9 (if that counts)
π: 3.14...; l: 108; i: 105; e: 101; l+i+e: 314
THE CAKE IS A LIE IS A PIE

Offline DJ Omnimaga

  • Now active at https://codewalr.us
  • CoT Emeritus
  • LV15 Omnimagician (Next: --)
  • *
  • Posts: 55821
  • Rating: +3151/-232
  • CodeWalrus founder & retired Omnimaga founder
    • View Profile
    • DJ Omnimaga Music
Re: Fast filled circles routine
« Reply #11 on: June 16, 2014, 11:22:29 am »
Not sure what the evals do and about the Angle, nor why it prompts me for which program to run at startup. I just took MacBernick code at http://www.omnimaga.org/hp-prime/fast-filled-circles-routine/?action=post;quote=373410;last_msg=386862 and replaced both colors and the FILLCIRCLE arguments so that the circle is always centered. Then I added DIMGROB/BLIT commands for the effect.
In case you are wondering where I went, I left Omni back in 2015 to form CodeWalrus due to various reasons explained back then, but I stopped calc dev in 2016 and am now mostly active on the CW Discord server at https://discord.gg/cuZcfcF


Bandcamp|Reverbnation|Facebook|Youtube|Twitter

Offline pimathbrainiac

  • Occasionally I make projects
  • Members
  • LV10 31337 u53r (Next: 2000)
  • **********
  • Posts: 1731
  • Rating: +136/-23
  • dagaem
    • View Profile
Re: Fast filled circles routine
« Reply #12 on: June 16, 2014, 11:23:33 am »
Every time I see cool stuff for the prime, it makes me wish my parents let me buy one...

Nice job!
I am Bach.

Offline DJ Omnimaga

  • Now active at https://codewalr.us
  • CoT Emeritus
  • LV15 Omnimagician (Next: --)
  • *
  • Posts: 55821
  • Rating: +3151/-232
  • CodeWalrus founder & retired Omnimaga founder
    • View Profile
    • DJ Omnimaga Music
Re: Fast filled circles routine
« Reply #13 on: June 16, 2014, 03:12:21 pm »
By the way, the S, 0, 359, 10 part can be changed to stuff like S, 0, 359, 20 for faster, but lower quality circle. Don't set the last number too high, else it looks weird. Lower results in higher quality, but slower circles and possible glitches when the circle becomes smaller.
In case you are wondering where I went, I left Omni back in 2015 to form CodeWalrus due to various reasons explained back then, but I stopped calc dev in 2016 and am now mostly active on the CW Discord server at https://discord.gg/cuZcfcF


Bandcamp|Reverbnation|Facebook|Youtube|Twitter

Offline Princetonlion.tibd

  • Agranovskiy Founder
  • Members
  • LV8 Addict (Next: 1000)
  • ********
  • Posts: 790
  • Rating: +3/-4
    • View Profile
    • Agranovskiy
Re: Fast filled circles routine
« Reply #14 on: June 16, 2014, 03:14:41 pm »
Now I wish I got a HP Prime instead of a V200
:P

It looks like it would be useful for games with circles.

Spoiler For my opinion:
Looks awesome!
Founder of Agranovskiy, a basic TI programming tutorial site.



I'm a USCF (United States Chess Federation) player.