Skip to main content
gamedev.net
🔒 Locked

Spring Question

Started by bargasteh Sep 3, 2005 at 3:43 PM 49 replies 5.6k views
Original Post
bargasteh
bargasteh
Hello all. I have a question about spring equation. I am making a fabric simulation and I wrote a simple spring simulation code to simulate spring and dashpot (the one which stop spring from moving too much, something like shock absorber). The code is here:

spring_dash_f.set(0,0,0);
vec3 spring_dash = box_array[Box_n2]->particles1[name1]->pos - box_array[Box_n1]->particles1[name2]->pos; 
float length = spring_dash.GetLength();
float displacement = length - originalLength; 
vec3 spring_dashN = spring_dash.GetNormalised();
spring_dash_f = spring_dashN*(((displacement)*K));
int extra = 1;


box_array[Box_n1]->particles1[name2]->addforce(box_array[Box_n1]->particles1[name2]->getforce() + spring_dash_f * extra);
box_array[Box_n1]->particles1[name1]->addforce(box_array[Box_n2]->particles1[name1]->getforce() - spring_dash_f * extra); 

As you can see I calculate the spring force and then apply it to the two masses, which are connected to spring. When I run the simulation, the springs get stretched too much due to masses and because I am using Euler I can't increase the K more than 90. Now the question is here: How can I make the springs to get stretched for example between 1 and 1.2 units? I mean how can I enforce the springs not to get stretched too much or gets too small? This is also very important as fabric becomes more realistic. Thank you so much in advance.
OpenGl + C++
blizzard999
blizzard999
Increase K and use a better integrator (Runge-Kutta IV or an implicit scheme).
Increase the friction and decrease the time step.
bargasteh
bargasteh
Yes, that is correct, but I have seen some people who use Euler but he wrote a function that enforce spring to get streched, basically this function keeps the lenght between the desire numbers.
Is there any of you who know what I can do to keep the spring lenght between a specific range?

Thanks
OpenGl + C++
Sweenie
Sweenie
In the linked article below, Mr. Gaffer shows the basics of springs(which I guess you already know).
But near the end of the article he mention that he will show in a future article how to handle what you are talking about, I guess.
Perhaps you could contact him and ask for a little preview?

Springs

<-Sweenie->
bargasteh
bargasteh
I did email him and invited him here, I hope he come here and give us some feedbacks.
meanwhile it would be great if anybody else know how we can do this?!
OpenGl + C++
Eelco
Eelco
Quote:
Original post by bargasteh
I did email him and invited him here, I hope he come here and give us some feedbacks.
meanwhile it would be great if anybody else know how we can do this?!


i think the technique youre looking for works like this:

instead of using euler, a (velocity-less) verlet integrator is used, which is just as simple to code. then, instead of applying forces, constrains are enforced by altering positions of the masses to conform to the springs length. this is repeated until the solution converges.

i believe there is a paper by some guy who worked on hitman who explains this technique. google for hitman physics and youre bound to find something.
blizzard999
blizzard999
One solution is to move the particles with some algorithms to correct the elongations; this one is harder than it seems because if you move a particle you modify also the spring length of the neighbours and it may introduce instability in the integration or even further over elongations.
In other words the risk is to introduce a cascade or a "domino" effect of over elongations.
However this method can be interesting to explore.

Another solution is to use a non linear spring coefficient: small when the spring is near its rest length, big when the spring is compressed or elongated.
This one is interesting because it simulates the physic behaviour of a real cloth in which the stretch resistance is something similar to an exponential; the drawback is that the problem becomes more "stiff" so to integrate the equation you have to reduce drastically the time step and/or modify the integrator.

When the problem is so stiff you probably cannot use Euler/Verlet but use at least the classic Runge-Kutta IV. RK IV is very simple to program but it does not work very well with stiff problems.
I could suggest you to use an implicit integrator but they are very hard to program although they are very very fast (you can use a GREATER time step). Consider that almost every real-time cloth simulation ( and not only ) use implicit schemes; be sure that with Euler and Verlet you will go not so far in these kind of problems (although they can be good enough in different situations)

Implicit schemes are usually simpler when you use a non physical correct model (like those used in demos and in games) because you can simplify the equations to program the solver.
bargasteh
bargasteh
What would be the best and the most stable system to simulate fabric in realtime?
mass-spring ? or something else?
OpenGl + C++
bargasteh
bargasteh
Thank you so much John Schultz.
When I finished reading the articles I became really confused over the whole thing, verlet and fixed time step and (e.g. "10% delta rule") :(

you were talking about:
---
|\|
---
which is look really promising. I think this structure is a lot better than the other one.
Could you please tell me what stepps I should take in order to have a fabric simulation running, using above structure?
I know you have talked about it on other threads but could you just sum up the whole thing so I will have a clearer idea about it.
I suppose:
1-I should have a verlet integrator running (currently Euler).
2-fix my time step, I am currently using this:
	float t = 0.0f;	float dt = 0.24f;	float currentTime = 0.0f;	float accumulator = 0.0f;        const float newTime = time();	float deltaTime = newTime - currentTime;					if (deltaTime>0.24f)			//continue;			deltaTime = 0.24f;					currentTime = newTime;		accumulator += deltaTime;		while (accumulator>=dt)		{			updateScene (0.024);//when i put dt here, the whole                                             //thing   explode			accumulator -= dt;			t+=dt;		}

3- change my structure to above one from:

A--B--C between A and C I have folding spring as well.
|\/|\/|
|/\|/\|
-------

Thank you
OpenGl + C++
bargasteh
bargasteh
I tried to use Verlet in my program but it didnt work, my code for Eular is:
Eualr
vec3 accl = grav + final_f + extra/mass;velo = velo + accl * (timestep);dis = velo * (timestep) + accl * (timestep*timestep)/2;pos = pos + dis;resetforce();


Verlet
float dt2 = timestep*timestep;vec3 accl = final_f + extra /mass;velo = pos - m_prevPos + accl * dt2;m_prevPos = pos;pos = pos + velo;resetforce();



When I move to verlet the whole system explode, masses fly all over the space, what is wrong with my code?
I didnt use any springs or constraints, masses are perfect when I use Eular but with didnt work with verlet :(
OpenGl + C++
Eelco
Eelco
Quote:
Original post by bargasteh
When I move to verlet the whole system explode, masses fly all over the space, what is wrong with my code?


"vec3 accl = final_f + extra /mass;"
didnt you forget parenthesis there?
bargasteh
bargasteh
No it didnt work.
I tried this and it didnt work.
vec3 total = grav+final_f+extra;float dt2 = timestep * timestep;vec3 accl = vec3(0,0,0) + total / mass;velo = pos - m_prevPos + accl * dt2;m_prevPos = pos;pos = pos + velo;
OpenGl + C++
jjd
jjd
Quote:
Original post by bargasteh
No it didnt work.
I tried this and it didnt work.
*** Source Snippet Removed ***


There seems to be a problem with your velocity calculation. Try this


vec3 total = grav+final_f+extra;
float dt2 = timestep * timestep;
vec3 accl = vec3(0,0,0) + total / mass;
del = pos - m_prevPos;
m_prevPos = pos;
pos = pos + del + accl * dt2;
velo = (pos - m_prevPos) / timestep;


-Josh

P.S. Apologies for not using the code snippet thing, but I can't get the plus symbol to appear. Can anyone tell me why that is?
Zakwayda
Zakwayda
Quote:
Apologies for not using the code snippet thing, but I can't get the plus symbol to appear. Can anyone tell me why that is?
I don't know why, but +'s are filtered in preview mode. They do however show up in the actual post.
jjd
jjd
Quote:
Original post by jyk
Quote:
Apologies for not using the code snippet thing, but I can't get the plus symbol to appear. Can anyone tell me why that is?
I don't know why, but +'s are filtered in preview mode. They do however show up in the actual post.


Cheers, jyk! :)
John Schultz
John Schultz
Quote:
Original post by bargasteh
When I finished reading the articles I became really confused over the whole thing, verlet and fixed time step and (e.g. "10% delta rule") :(


The "10% rule" means that if the spring length changes more than 10% of its length, don't apply a spring force. Instead, treat the spring (link) as a Verlet rigid constraint (which is 100% stable). "10%" was taken from the ILM paper; I used values based on testing the system (including just clamping force/accel to a maximum value). Thus "10%" is arbitrary (depends on timestep, etc.).
bargasteh
bargasteh
My verlet is not working dear John,
Please please will you give me a hand to make it work?

Thank you
OpenGl + C++
John Schultz
John Schultz
Quote:
Original post by bargasteh
My verlet is not working dear John,
Please please will you give me a hand to make it work?

Thank you


Hi bargesteh,

Sorry I can't spend more time on this right now. If you look at the post in my link above where I list items 1., 2., 3., (starting with a particle), you should be able to get your system to work by following those steps.
bargasteh
bargasteh
Thank you john, I will try to figure it out somehow.

Is there any body else who can tell me how I can use Verlet in a simple mass-spring system?

The only thing i want to do now is to use verlet in the same as euler where I can put fee masses above ground and then realease them and let gravity to hangle them.

is there anybody who can give me a pseudo code?

I can use simple Euler to drop a mass but when I use the Verlet the whole thing explode.

Thank you.
OpenGl + C++

Topic Locked

This topic has been locked by a moderator. New replies are not allowed.

Sign in to reply to this topic.