You are not logged in.
Pages: 1
draw advanced star
tested on GM8 and GM:S
/// draw_star_ext(Points,X,Y,Rad,Rad2,Rot,XScale,YScale,OutLine,Clr1,Clr2,Alpha)
/// GMLscripts.com/license
var A,B,X,Y,Pnt,Rad,CR,Rot,XScl,YScl,N; CR=0;
Pnt=floor(abs(argument0))*2; //number of points
X=argument1; //x position
Y=argument2; //y position
Rad[0]=argument3; //radius 1
Rad[1]=argument4; //radius 2 (shorter)
Rot=argument5; //rotation
XScl=argument6; //x scale
YScl=argument7; //y scale
OutL=argument8; //outline
Clr[0]=argument9; //color 1
Clr[1]=argument10; //color 2
if (OutL) draw_primitive_begin(pr_linestrip); else
{
draw_primitive_begin(pr_trianglefan);
draw_vertex_color(X,Y,Clr[0],argument11);
}
for(N=0; N<=Pnt; N+=1)
{
A=X+lengthdir_x(Rad[CR],Rot+360*N/Pnt)*XScl;
B=Y+lengthdir_y(Rad[CR],Rot+360*N/Pnt)*YScl;
draw_vertex_color(A,B,Clr[CR],argument11); CR=!CR;
}
draw_primitive_end();
you may need to edit this script to meet you needs
example :
draw_star_ext(5,mouse_x,mouse_y,100,50,33,2,1,false,c_red,c_yellow,1);
Offline
This is a great script. I'm sure many people will find this useful. The only issue is the use of pr_trianglefan
. A triangle fan is the obvious choice when writing a script like this. Unfortunately, this kind of primitive is an old Direct3D relic that isn't available on all platforms, like HTML5 and some devices. Before I add it to the site, I'll probably rewrite it to be more compatible. If you want to update it yourself, please do.
Thanks, omar, and welcome to the forums.
Abusing forum power since 1986.
Offline
what you recommend me to use instead of pr_trianglefan
Last edited by omar (2016-06-25 06:52:25)
Offline
I think a pr_trianglelist
is the only option. I don't see a way to construct a star shape like this using a pr_trianglestrip
.
Spoiler: http://hastebin.com/raw/rarayavano
Abusing forum power since 1986.
Offline
no , there is a way to draw the same star using pr_trianglestrip
without using extra memory
/// draw_star_ext(Points,X,Y,Rad,Rad2,Rot,XScale,YScale,OutLine,Clr1,Clr2,Alpha)
/// GMLscripts.com/license
var A,B,X,Y,Pnt,Rad,CR,Rot,XScl,YScl,N;
Pnt=floor(abs(argument0))*2; //number of points
X=argument1; //x position
Y=argument2; //y position
Rad[0]=argument3; //radius 1
Rad[1]=argument4; //radius 2 (shorter)
Rot=argument5; //rotation
XScl=argument6; //x scale
YScl=argument7; //y scale
OutL=argument8; //outline
Clr[0]=argument9; //color 1
Clr[1]=argument10; //color 2
CR=0;
if (OutL)
{
draw_primitive_begin(pr_linestrip)
for(N=0; N<=Pnt; N+=1)
{
A=X+lengthdir_x(Rad[CR],Rot+360*N/Pnt)*XScl;
B=Y+lengthdir_y(Rad[CR],Rot+360*N/Pnt)*YScl;
draw_vertex_color(A,B,Clr[CR],argument11);
CR=!CR;
}
}
else
{
draw_primitive_begin(pr_trianglestrip);
for(N=0; N<=Pnt; N+=1)
{
A=X+lengthdir_x(Rad[CR],Rot+360*N/Pnt)*XScl;
B=Y+lengthdir_y(Rad[CR],Rot+360*N/Pnt)*YScl;
draw_vertex_color(A,B,Clr[CR],argument11);
A=X+lengthdir_x(0,Rot+360*N/Pnt)*XScl;
B=Y+lengthdir_y(0,Rot+360*N/Pnt)*YScl;
draw_vertex_color(A,B,Clr[0],argument11);
CR=!CR;
}
}
draw_primitive_end();
and if you don't like the coloring style
there is another method
change the second loop to this
for(N=0; N<=Pnt; N+=1)
{
A=X+lengthdir_x(Rad[CR],Rot+360*N/Pnt)*XScl;
B=Y+lengthdir_y(Rad[CR],Rot+360*N/Pnt)*YScl;
draw_vertex_color(A,B,Clr[1],argument11);
A=X+lengthdir_x(0,Rot+360*N/Pnt)*XScl;
B=Y+lengthdir_y(0,Rot+360*N/Pnt)*YScl;
draw_vertex_color(A,B,Clr[0],argument11);
CR=!CR;
}
Last edited by omar (2016-07-01 11:05:49)
Offline
Yeah, you can do it that way if you don't mind degenerate triangles. From what I've read today, modern hardware handles them OK. There used to be warnings not to use them, which is why I avoid them.
In terms of performance, there is more overhead to using strips over lists but I don't think that probably matters in any practical sense with this script.
One important thing I didn't address before is winding order. If back face culling is enabled, ie. d3d_set_culling(true)
, your triangles would not be drawn. The points needed to be given in a different order. Your new script fixes that so this is no longer a problem.
Finally, I would optimize lengthdir_x/y(0, dir). If the length is zero, the result is also zero. A=X+lengthdir_x(0,Rot+360*N/Pnt)*XScl;
could just be A=X;
. Of course you could skip the assignment altogether and do this:
{
A=X+lengthdir_x(Rad[CR],Rot+360*N/Pnt)*XScl;
B=Y+lengthdir_y(Rad[CR],Rot+360*N/Pnt)*YScl;
draw_vertex_color(A,B,Clr[CR],argument11);
draw_vertex_color(X,Y,Clr[0],argument11);
CR=!CR;
}
Abusing forum power since 1986.
Offline
Pages: 1