Home
JAQForum Ver 20.06
Log In or Join  
Active Topics
Local Time 03:12 05 May 2024 Privacy Policy
Jump to

Notice. New forum software under development. It's going to miss a few functions and look a bit ugly for a while, but I'm working on it full time now as the old forum was too unstable. Couple days, all good. If you notice any issues, please contact me.

Forum Index : Microcontroller and PC projects : MM2: 4.7b Bezier curves

Author Message
matherp
Guru

Joined: 11/12/2012
Location: United Kingdom
Posts: 8592
Posted: 01:43am 30 May 2015
Copy link to clipboard 
Print this post

One of the new features in 4.7b8 is the ability to work with floating point numbers inside Cfunctions. The attached example wouldn't have been possible previously




option default none
option explicit
dim integer i
timer=0
i=bezier(10,10,106,80,212,80,309,10,rgb(yellow))
i=bezier(10,230,106,150,212,150,309,230,rgb(yellow))
i=bezier(10,10,80,80,80,160,10,230,rgb(green))
i=bezier(309,10,239,80,239,160,309,230,rgb(green))
text 85,110,"Cubic Bezier Curves"
print timer
end

' Function to plot Bezier Cubic Splines
'
' Parameters are:
' X coordinate of start point
' Y coordinate of start point
' X coordinate of first control point
' Y coordinate of first control point
' X coordinate of second control point
' Y coordinate of second control point
' X coordinate of end point
' Y coordinate of end point
' Colour of curve
'
CFunction bezier
00000000
27bdff78 afb00060 3c109d00 8e020080 afb10064 00a08821 8c850004 8c840000
afbf0084 afa70054 afb50074 afa6005c afbe0080 afb7007c afb60078 afb40070
afb3006c afb20068 0040f809 8fb500a8 8fa6005c afa20030 8cc40000 8e020080
0040f809 8cc50004 afa20034 8fa20098 8c440000 8c450004 8e020080 0040f809
00000000 afa20038 8fa200a0 8c440000 8c450004 8e020080 0040f809 00000000
afa2003c 8e240000 8e020080 0040f809 8e250004 8fa70054 afa20040 8ce40000
8e020080 0040f809 8ce50004 afa20044 8fa2009c 8c440000 8c450004 8e020080
0040f809 00000000 8fa300a4 afa20048 8c640000 8e020080 0040f809 8c650004
afa2004c 3c023f80 00409821 3c024000 0040a021 3c024040 00409021 3c023a83
3442126f 00401021 2403ffff afa20050 afa3002c 2416ffff 10000098 00008821
02602021 0040f809 02202821 0040b821 8e020074 02202021 0040f809 02402821
afa20018 8e020074 02e02021 0040f809 02402821 afa2001c 8e020074 02202021
0040f809 02802821 0040f021 8e020074 02e02021 0040f809 02802821 afa20020
8e020058 02402021 0040f809 02202821 afa20024 8e020058 03c02821 0040f809
02402021 afa20028 8fa4001c 8fa50030 8e020058 0040f809 8e1e005c 8e030058
8fa40020 8fa50034 afa30058 0060f809 afa2005c 8fa30058 8fa40024 0060f809
00402821 8fa6005c 00402821 03c0f809 00c02021 8e030058 8fa50038 02e02021
afa30058 0060f809 afa2005c 8fa30058 8fa40028 0060f809 00402821 8fa6005c
00402821 03c0f809 00c02021 00401821 8fa40018 8e020058 8fa5003c 0040f809
afa30058 8fa30058 00402821 03c0f809 00602021 00403021 8fa4001c 8e020058
8fa50040 8e1e005c 0040f809 afa6005c 8e030058 8fa40020 8fa50044 afa30058
0060f809 afa20054 8fa30058 8fa40024 0060f809 00402821 8fa70054 00402821
03c0f809 00e02021 8e030058 8fa50048 02e02021 afa30058 0060f809 afa20054
8fa30058 8fa40028 0060f809 00402821 8fa70054 00402821 03c0f809 00e02021
0040b821 8fa40018 8e020058 0040f809 8fa5004c 00402821 03c0f809 02e02021
8fa6005c 0040f021 8e02007c 0040f809 00c02021 0040b821 8e02007c 0040f809
03c02021 56f60005 8ea30000 8fa3002c 5043000d 8e02005c 8ea30000 00402821
afa30010 8e030048 00403821 afa20054 02e02021 0060f809 02e03021 8fa20054
afa2002c 8e02005c 8fa50050 0040f809 02202021 00408821 02e0b021 8e020068
02202021 0040f809 02602821 2403ffff 5043ff63 8e020060 8fbf0084 00001021
00001821 8fbe0080 8fb7007c 8fb60078 8fb50074 8fb40070 8fb3006c 8fb20068
8fb10064 8fb00060 03e00008 27bd0088
End CFunction 'MIPS32 M4K
'
'
'long long bezier (long long *xx0, long long *yy0, long long *xx1, long long *yy1,long long *xx2, long long *yy2, long long *xx3, long long *yy3, long long *colour)
'{
' float tmp,tmp1,tmp2,tmp3,tmp4,tmp5,tmp6,t,xt,yt;
' float x0=IntToFloat(*xx0),x1=IntToFloat(*xx1),x2=IntToFloat(*xx2),x3=IntToFloat(*xx3);
' float y0=IntToFloat(*yy0),y1=IntToFloat(*yy1),y2=IntToFloat(*yy2),y3=IntToFloat(*yy3);
' int xti,yti,xtlast=-1, ytlast=-1;
' K_1(one)
' K_2(two)
' K_3(three)
' K_ANY(inc,0x3A83126F) //0.001
'
' for (t = 0x0; FCmp(t , one)==-1; t=FAdd(t,inc))
' {
' tmp=FSub(one,t);
' tmp1=FPow(t, three);
' tmp2=FPow(tmp, three);
' tmp3=FPow(t, two);
' tmp4=FPow(tmp, two);
' tmp5=FMul(three , t);
' tmp6=FMul(three , tmp3);
' xt = FAdd(FAdd(FAdd(FMul(tmp2 , x0) ,
' FMul(tmp5 , FMul(tmp4 , x1))) ,
' FMul(tmp6 , FMul(tmp , x2))) ,
' FMul(tmp1 , x3));
'
' yt = FAdd(FAdd(FAdd(FMul(tmp2 ,y0) ,
' FMul(tmp5 , FMul(tmp4 , y1))) ,
' FMul(tmp6 , FMul(tmp , y2))) ,
' FMul(tmp1 , y3));
' xti=FloatToInt(xt);
' yti=FloatToInt(yt);
'
' if((xti!=xtlast) || (yti!=ytlast)) {
' DrawPixel(xti, yti, *colour);
' xtlast=xti;
' ytlast=yti;
' }
' }
' return 0;
'

Edited by matherp 2015-05-31
 
paceman
Guru

Joined: 07/10/2011
Location: Australia
Posts: 1328
Posted: 03:23am 30 May 2015
Copy link to clipboard 
Print this post

We'll be smoothing skewed Gaussian distributions soon Peter - just when I thought I'd forgotten my X-ray diffraction days!
Now what was that pattern recognition job for the Micromite we were all thinking about.

Greg
 
matherp
Guru

Joined: 11/12/2012
Location: United Kingdom
Posts: 8592
Posted: 05:20am 30 May 2015
Copy link to clipboard 
Print this post

One thing you can do with Bezier curves is use them to plot arcs. To do this a bit of maths is required to calculate the control points.




But you can then plot any arbitrary arcs


option default none
option explicit
dim integer i
timer=0
for i=0 to 99 step 4
LargeArc(mm.hres/2,mm.vres/2,20+i,325+2*i,5+5*i,rgb(yellow))
next i
print timer
end
'
' subroutine to calculate points to use cubic Bezier splines to plot arcs greater than 90 degrees
'
' Parameters are:
' X coordinate of centre of arc
' Y coordinate of centre of arc
' radius of arc
' start radial of arc in degrees
' end radial of arc in degrees
'
sub LargeArc(x as integer, y as integer, r as integer, a1i as integer, a2i as integer, col as integer)
local integer amid, astart=a1i
if a2i<a1i then a2i=a2i+360
do while a2i-astart>90
SmallArc(x , y , r , astart, astart+90 , col)
astart=astart+90
loop
SmallArc(x , y , r , astart, a2i , col)
end sub
'
' subroutine to calculate points to use cubic Bezier splines to plot arcs less than 90 degrees
'
' Parameters are:
' X coordinate of centre of arc
' Y coordinate of centre of arc
' radius of arc
' start radial of arc in degrees
' end radial of arc in degrees

sub SmallArc(x as integer, y as integer, ri as integer, a1i as integer, a2i as integer, col as integer)
' Compute all four points for an arc that subtends the same total angle
' but is centered on the X-axis
local float r,a1,a2,a,x1,y1,x2,y2,x3,y3,x4,y4,k,f,ar,cos_ar,sin_ar
local integer j,x1i,x2i,x3i,x4i,y1i,y2i,y3i,y4i
r=ri
a1=rad(a1i)- pi/2
a2=rad(a2i) -pi/2
a = (a2-a1) / 2.0
x4 = r * cos(a)
y4 = r * sin(a)
x1= x4
y1= -y4
k = 0.5522847498
f = k * tan(a)
x2 = x1 + f * y4
y2 = y1 + f * x4
x3 = x2
y3= -y2
' Find the arc points actual locations by computing x1,y1 and x4,y4
' and rotating the control points by a + a1
ar = a + a1
cos_ar = cos(ar)
sin_ar = sin(ar)
x1i = r * cos(a1) + x
y1i = r * sin(a1) + y
x2i = x2 * cos_ar - y2 * sin_ar + x
y2i = x2 * sin_ar + y2 * cos_ar + y
x3i = x3 * cos_ar - y3 * sin_ar + x
y3i = x3 * sin_ar + y3 * cos_ar + y
x4i = r * cos(a2) + x
y4i = r * sin(a2) + y
j=bezier(x1i,y1i,x2i,y2i,x3i,y3i,x4i,y4i,col)
end sub
'
' Function to plot Bezier Cubic Splines
'
' Parameters are:
' X coordinate of start point
' Y coordinate of start point
' X coordinate of first control point
' Y coordinate of first control point
' X coordinate of second control point
' Y coordinate of second control point
' X coordinate of end point
' Y coordinate of end point
' Colour of curve
'
CFunction bezier
00000000
27bdff78 afb00060 3c109d00 8e020080 afb10064 00a08821 8c850004 8c840000
afbf0084 afa70054 afb50074 afa6005c afbe0080 afb7007c afb60078 afb40070
afb3006c afb20068 0040f809 8fb500a8 8fa6005c afa20030 8cc40000 8e020080
0040f809 8cc50004 afa20034 8fa20098 8c440000 8c450004 8e020080 0040f809
00000000 afa20038 8fa200a0 8c440000 8c450004 8e020080 0040f809 00000000
afa2003c 8e240000 8e020080 0040f809 8e250004 8fa70054 afa20040 8ce40000
8e020080 0040f809 8ce50004 afa20044 8fa2009c 8c440000 8c450004 8e020080
0040f809 00000000 8fa300a4 afa20048 8c640000 8e020080 0040f809 8c650004
afa2004c 3c023f80 00409821 3c024000 0040a021 3c024040 00409021 3c023a83
3442126f 00401021 2403ffff afa20050 afa3002c 2416ffff 10000098 00008821
02602021 0040f809 02202821 0040b821 8e020074 02202021 0040f809 02402821
afa20018 8e020074 02e02021 0040f809 02402821 afa2001c 8e020074 02202021
0040f809 02802821 0040f021 8e020074 02e02021 0040f809 02802821 afa20020
8e020058 02402021 0040f809 02202821 afa20024 8e020058 03c02821 0040f809
02402021 afa20028 8fa4001c 8fa50030 8e020058 0040f809 8e1e005c 8e030058
8fa40020 8fa50034 afa30058 0060f809 afa2005c 8fa30058 8fa40024 0060f809
00402821 8fa6005c 00402821 03c0f809 00c02021 8e030058 8fa50038 02e02021
afa30058 0060f809 afa2005c 8fa30058 8fa40028 0060f809 00402821 8fa6005c
00402821 03c0f809 00c02021 00401821 8fa40018 8e020058 8fa5003c 0040f809
afa30058 8fa30058 00402821 03c0f809 00602021 00403021 8fa4001c 8e020058
8fa50040 8e1e005c 0040f809 afa6005c 8e030058 8fa40020 8fa50044 afa30058
0060f809 afa20054 8fa30058 8fa40024 0060f809 00402821 8fa70054 00402821
03c0f809 00e02021 8e030058 8fa50048 02e02021 afa30058 0060f809 afa20054
8fa30058 8fa40028 0060f809 00402821 8fa70054 00402821 03c0f809 00e02021
0040b821 8fa40018 8e020058 0040f809 8fa5004c 00402821 03c0f809 02e02021
8fa6005c 0040f021 8e02007c 0040f809 00c02021 0040b821 8e02007c 0040f809
03c02021 56f60005 8ea30000 8fa3002c 5043000d 8e02005c 8ea30000 00402821
afa30010 8e030048 00403821 afa20054 02e02021 0060f809 02e03021 8fa20054
afa2002c 8e02005c 8fa50050 0040f809 02202021 00408821 02e0b021 8e020068
02202021 0040f809 02602821 2403ffff 5043ff63 8e020060 8fbf0084 00001021
00001821 8fbe0080 8fb7007c 8fb60078 8fb50074 8fb40070 8fb3006c 8fb20068
8fb10064 8fb00060 03e00008 27bd0088
End CFunction 'MIPS32 M4K
'
'
'long long bezier (long long *xx0, long long *yy0, long long *xx1, long long *yy1,long long *xx2, long long *yy2, long long *xx3, long long *yy3, long long *colour)
'{
' float tmp,tmp1,tmp2,tmp3,tmp4,tmp5,tmp6,t,xt,yt;
' float x0=IntToFloat(*xx0),x1=IntToFloat(*xx1),x2=IntToFloat(*xx2),x3=IntToFloat(*xx3);
' float y0=IntToFloat(*yy0),y1=IntToFloat(*yy1),y2=IntToFloat(*yy2),y3=IntToFloat(*yy3);
' int xti,yti,xtlast=-1, ytlast=-1;
' K_1(one)
' K_2(two)
' K_3(three)
' K_ANY(inc,0x3A83126F) //0.001
'
' for (t = 0x0; FCmp(t , one)==-1; t=FAdd(t,inc))
' {
' tmp=FSub(one,t);
' tmp1=FPow(t, three);
' tmp2=FPow(tmp, three);
' tmp3=FPow(t, two);
' tmp4=FPow(tmp, two);
' tmp5=FMul(three , t);
' tmp6=FMul(three , tmp3);
' xt = FAdd(FAdd(FAdd(FMul(tmp2 , x0) ,
' FMul(tmp5 , FMul(tmp4 , x1))) ,
' FMul(tmp6 , FMul(tmp , x2))) ,
' FMul(tmp1 , x3));
'
' yt = FAdd(FAdd(FAdd(FMul(tmp2 ,y0) ,
' FMul(tmp5 , FMul(tmp4 , y1))) ,
' FMul(tmp6 , FMul(tmp , y2))) ,
' FMul(tmp1 , y3));
' xti=FloatToInt(xt);
' yti=FloatToInt(yt);
'
' if((xti!=xtlast) || (yti!=ytlast)) {
' DrawPixel(xti, yti, *colour);
' xtlast=xti;
' ytlast=yti;
' }
' }
' return 0;
'
 
paceman
Guru

Joined: 07/10/2011
Location: Australia
Posts: 1328
Posted: 06:09pm 30 May 2015
Copy link to clipboard 
Print this post

That's sure making it work Peter - took around 6420mS on mine, but it's very pretty! I'm also pretty sure at this stage my head is hurting.

I Googled 'Bezier curves' yesterday and one of the links here mentioned that PostScript fonts are defined using them these days. Interesting stuff - you can certainly understand that when you look at your demo above.

Greg
 
matherp
Guru

Joined: 11/12/2012
Location: United Kingdom
Posts: 8592
Posted: 02:31am 31 May 2015
Copy link to clipboard 
Print this post

Hi paceman

I've spent a bit of time optimising - try this
now averaging 40msec / arc which seems OK



option default none
option explicit
cpu 48
const k = 0.5522847498
const pidiv2=pi/2
dim integer i
timer=0
for i=0 to 99 step 4
LargeArc(mm.hres/2,mm.vres/2,20+i,325+2*i,5+5*i,rgb(yellow))
next i
print timer
end
'
' subroutine to calculate points to use cubic Bezier splines to plot arcs greater than 90 degrees
'
' Parameters are:
' X coordinate of centre of arc
' Y coordinate of centre of arc
' radius of arc
' start radial of arc in degrees
' end radial of arc in degrees
sub LargeArc(x as integer, y as integer, r as integer, a1i as integer, a2i as integer, col as integer)
local integer amid, astart=a1i
if a2i<a1i then a2i=a2i+360
do while a2i-astart>90
SmallArc(x , y , r , astart, astart+90 , col)
astart=astart+90
loop
SmallArc(x , y , r , astart, a2i , col)
end sub
'
' subroutine to calculate points to use cubic Bezier splines to plot arcs less than 90 degrees
'
' Parameters are:
' X coordinate of centre of arc
' Y coordinate of centre of arc
' radius of arc
' start radial of arc in degrees
' end radial of arc in degrees

sub SmallArc(x as integer, y as integer, ri as integer, a1i as integer, a2i as integer, col as integer)
' First compute all four points for an arc that subtends the same total angle
' but is centered on the X-axis
local float r,a1,a2,a,x1,y1,x2,y2,x3,y3,x4,y4,f,ar,cos_ar,sin_ar
local integer j
local float x2i,x3i,y2i,y3i
r=ri
a1=rad(a1i)- pidiv2
a2=rad(a2i)- pidiv2
a = (a2-a1) / 2.0
x4 = r * cos(a)
y4 = r * sin(a)
x1= x4
y1= -y4
f = k * tan(a)
x2 = x1 + f * y4
y2 = y1 + f * x4
x3 = x2
y3= -y2
' Now find the arc points actual locations by computing x1,y1 and x4,y4
' and rotating the control points by a + a1
ar = a + a1
cos_ar = cos(ar)
sin_ar = sin(ar)
x1 = r * cos(a1) + x
y1 = r * sin(a1) + y
x2i = x2 * cos_ar - y2 * sin_ar + x
y2i = x2 * sin_ar + y2 * cos_ar + y
x3i = x3 * cos_ar - y3 * sin_ar + x
y3i = x3 * sin_ar + y3 * cos_ar + y
x4 = r * cos(a2) + x
y4 = r * sin(a2) + y
j=fbezier(x1,y1,x2i,y2i,x3i,y3i,x4,y4,col)
end sub
'
' Function to plot Bezier Cubic Splines
'
' Parameters are:
' X coordinate of start point
' Y coordinate of start point
' X coordinate of first control point
' Y coordinate of first control point
' X coordinate of second control point
' Y coordinate of second control point
' X coordinate of end point
' Y coordinate of end point
' Colour of curve
'
CFunction fbezier
00000000
27bdffa0 2402ffff afbe0058 afb70054 afb60050 afb5004c afb40048 afb30044
afb1003c afb00038 00c0a821 afbf005c afb20040 0080b821 00a0b021 00e0a021
8fbe0080 241301f4 afa20028 2406ffff 00008821 10000002 3c109d00 02403021
3c023f80 00402021 8e020060 02202821 0040f809 afa60034 00409021 8e020058
02202021 0040f809 02202821 afa20018 8e020058 02402021 0040f809 02402821
afa2001c 8fa40018 8e020058 0040f809 02202821 afa20020 8fa4001c 8e020058
0040f809 02402821 afa20024 3c024040 00402021 8e020058 0040f809 02202821
00403821 3c024040 00402021 8e020058 8fa50018 0040f809 afa7002c 8fa7002c
00401821 8fa5001c 8e020058 00e02021 0040f809 afa30030 8fa30030 afa20018
8e020058 00602021 0040f809 02402821 afa2001c 8ee50000 8fa40024 8e020058
0040f809 8e12005c 00401821 8ea50000 8e020058 8fa40018 0040f809 afa30030
8fa30030 00402821 0240f809 00602021 8fa40070 00401821 8c850000 8e020058
8fa4001c 0040f809 afa30030 8fa30030 00402821 0240f809 00602021 8fa40078
00401821 8c850000 8e020058 8fa40020 0040f809 afa30030 8fa30030 00402821
0240f809 00602021 00401821 8ec50000 8e020058 8fa40024 8e12005c 0040f809
afa30030 00403821 8e850000 8e020058 8fa40018 0040f809 afa7002c 8fa7002c
00402821 0240f809 00e02021 8fa40074 00403821 8c850000 8e020058 8fa4001c
0040f809 afa7002c 8fa7002c 00402821 0240f809 00e02021 8fa4007c 00403821
8c850000 8e020058 8fa40020 0040f809 afa7002c 8fa7002c 00402821 0240f809
00e02021 8fa30030 00402821 8e02007c 00602021 0040f809 afa5002c 8fa5002c
00409021 8e02007c 0040f809 00a02021 8fa60034 56460005 8fc30000 8fa30028
1043000c 00000000 8fc30000 00402821 afa30010 8e030048 00403821 afa2002c
02402021 0060f809 02403021 8fa2002c afa20028 3c023b03 3442126f 00402821
8e02005c 0040f809 02202021 2673ffff 1660ff5a 00408821 8fbf005c 00001021
00001821 8fbe0058 8fb70054 8fb60050 8fb5004c 8fb40048 8fb30044 8fb20040
8fb1003c 8fb00038 03e00008 27bd0060
End CFunction 'MIPS32 M4K
'long long fbezier (float *x0, float *y0, float *x1, float *y1,float *x2, float *y2, float *x3, float *y3, long long *colour)
'{
' float tmp,tmp1,tmp2,tmp3,tmp4,tmp5,tmp6,tmp7,tmp8,t,xt,yt;
' int xti,yti,xtlast=-1, ytlast=-1;
' int i;
' t = 0x0;
' for (i=0;i<500;i++)
' {
' tmp =FSub(M_1,t);
' tmp3=FMul(t,t);
' tmp4=FMul(tmp,tmp);
' tmp1=FMul(tmp3,t);
' tmp2=FMul(tmp4,tmp);
' tmp5=FMul(M_3, t);
' tmp6=FMul(M_3, tmp3);
' tmp7=FMul(tmp5,tmp4);
' tmp8=FMul(tmp6,tmp);
' xt = FAdd(FAdd(FAdd(FMul(tmp2 , *x0) ,
' FMul(tmp7 , *x1)) ,
' FMul(tmp8 , *x2)) ,
' FMul(tmp1 , *x3));
'
' yt = FAdd(FAdd(FAdd(FMul(tmp2 ,*y0) ,
' FMul(tmp7 , *y1)) ,
' FMul(tmp8 , *y2)) ,
' FMul(tmp1 , *y3));
' xti=FloatToInt(xt);
' yti=FloatToInt(yt);
' if((xti!=xtlast) || (yti!=ytlast)) {
' DrawPixel(xti, yti, *colour);
' xtlast=xti;
' ytlast=yti;
' }
' t=FAdd(t,M_ANY(0x3B03126F));
' }
' return 0;
'
 
paceman
Guru

Joined: 07/10/2011
Location: Australia
Posts: 1328
Posted: 04:40am 31 May 2015
Copy link to clipboard 
Print this post

That's 2250 on mine to run the whole thing above - 25 arcs plus all the other calcs, about a third of the previous code run time. It's difficult now to see each arc being plotted, they just individually appear whereas before you could follow them being plotted.
Quite impressive Peter, I'm glad you seem to know what you're doing.
 
WhiteWizzard
Guru

Joined: 05/04/2013
Location: United Kingdom
Posts: 2794
Posted: 06:32am 31 May 2015
Copy link to clipboard 
Print this post

Greg, Peter,

What are the resolutions of the TFTs you are using? And also which controller - Thanks

WW
For everything Micromite visit micromite.org

Direct Email: whitewizzard@micromite.o
 
matherp
Guru

Joined: 11/12/2012
Location: United Kingdom
Posts: 8592
Posted: 07:25am 31 May 2015
Copy link to clipboard 
Print this post

  Quote  What are the resolutions of the TFTs you are using? And also which controller


240x320 ili9341
 
paceman
Guru

Joined: 07/10/2011
Location: Australia
Posts: 1328
Posted: 03:19pm 31 May 2015
Copy link to clipboard 
Print this post


Same here: 240x320 ILI9341. I'm using a 2.8" and a 2.4", they both have pretty much exactly the same timing.

Greg
 
Print this page


To reply to this topic, you need to log in.

© JAQ Software 2024