@gnysek Trzeba dodać kolorowanie GMLa do forum.
Sporo można tutaj jeszcze z optymalizować, na pewno fajnie byłoby się pozbyć trygonometrii i obliczać wszystko na wektorach ale w tym jestem kiepski
oRope Create:
///
us2s = 1/1000000; // conversion micro sec to sec
grav = 980;
ropeLen = 600;
dotNum = 30;
/* more iterations means better precision
and stronger connections between dots but it's slower to compute
*/
constraintsIterations = 3;
dotConDist = ropeLen/dotNum;
for ( var i = 0; i <= dotNum; i++ )
{
dotX[i] = x+random_range(-1, 1);
dotY[i] = y+i;
dotXprev[i] = dotX[i];
dotYprev[i] = dotY[i];
dotXforce[i] = 0;
dotYforce[i] = grav;
}
oRope: Step
/// Satisfy Constraints
repeat constraintsIterations
{
// Springs
for ( var i = 0; i < dotNum; i++ )
{
var vel = point_distance(dotX[i], dotY[i], dotX[i+1], dotY[i+1]);
var velD = point_direction(dotX[i], dotY[i], dotX[i+1], dotY[i+1]);
vel *= dotConDist*dotConDist/(vel*vel+dotConDist*dotConDist)-0.5; // Ten wzór jest z GamaSutry
dotX[i] -= lengthdir_x(vel, velD);
dotX[i+1] += lengthdir_x(vel, velD);
dotY[i] -= lengthdir_y(vel, velD);
dotY[i+1] += lengthdir_y(vel, velD);
}
// pin root dot to screen
dotX[0] = x;
dotY[0] = y;
// move last dot to mouse
if ( mouse_check_button(mb_left) )
{
dotX[dotNum] = mouse_x;
dotY[dotNum] = mouse_y;
}
// move root dot to mouse
if ( mouse_check_button(mb_right) )
{
x = mouse_x;
y = mouse_y;
}
// collision
for ( var i = 0; i <= dotNum; i++ )
{
var vX = dotX[i]-dotXprev[i];
var vY = dotY[i]-dotYprev[i];
if ( position_meeting(dotX[i]+vX, dotY[i], oCollider) )
dotX[i] = dotXprev[i];
if ( position_meeting(dotX[i], dotY[i]+vY, oCollider) )
dotY[i] = dotYprev[i];
}
// Implements particles in a box
for ( var i = 0; i <= dotNum; i++ )
{
dotX[i] = clamp(dotX[i], 64, 960 );
dotY[i] = clamp(dotY[i], 64, 722 );
}
}
oRope: end step
/// Verlet update
var dt = delta_time * us2s;
for ( var i = 0; i <= dotNum; i++ )
{
var tempX = dotX[i];
var tempY = dotY[i];
dotX[i] += dotX[i] - dotXprev[i] + dotXforce[i]*dt*dt;
dotY[i] += dotY[i] - dotYprev[i] + dotYforce[i]*dt*dt;
dotXprev[i] = tempX;
dotYprev[i] = tempY;
}
oRope: Draw
///
draw_set_color(c_red);
for ( var i = 0; i <= dotNum; i++ )
{
if (i > 0) draw_line_width( dotX[i], dotY[i], dotX[i-1], dotY[i-1], 3);
draw_sprite( sDot, 1, dotX[i], dotY[i] );
}
draw_sprite( sDot, 0, dotX[0], dotY[0] );