|
-
Apr 14th, 2011, 06:08 PM
#1
Thread Starter
Stack Overflow moderator
Physics and realistic motion in 2 dimensions
I'm making a game where the main character is a white blood cell. Right now I have a circle. 360 points. I want my character to squish against walls, jiggle while moving, etc... but I'm just at a loss as to how to even start doing this. What's the best way to implement that kind of 2-d physics?
-
Apr 14th, 2011, 06:34 PM
#2
Re: Physics and realistic motion in 2 dimensions
Sounds like you want to apply a "damped spring" force between adjacent points. When combined with all your other forces (gravity, collision, etc) it should give you the sort of reaction you're after to the shape of your cell. It won't necessarily cause jiggling while moving, you'd probably have to add in some additional force to set that off.
Once you've got all your forces, it's simply a case of taking the position and velocity of the point, applying the force and working out the position and velocity of the next time slice. You shouldn't have much trouble googling for many resources on that front. The most important piece of advice beyond the mathematics itself is to make sure you divorce "simulation time" from "real world time".
-
Apr 15th, 2011, 10:33 AM
#3
Re: Physics and realistic motion in 2 dimensions
Your learning C right?
Check out the Gish source code.
I believe the blob is defined with 12 points. Each point connects to the opposite point and the 2 adjacent points via virtual springs.
-
Apr 15th, 2011, 01:02 PM
#4
Thread Starter
Stack Overflow moderator
Re: Physics and realistic motion in 2 dimensions
That website is filtered for me because of malicious content, but I'll try looking at it on another computer soon. Thanks.
-
Apr 15th, 2011, 09:14 PM
#5
Thread Starter
Stack Overflow moderator
Re: Physics and realistic motion in 2 dimensions
Okay, I tried making my own spring system based on someone else's advice:
Code:
Public Class Particle
Private _location As PointF
Private _velocity As PointF
Private _friction As Single
Private _frame As RectangleF
Public Sub New()
_friction = 0.15!
End Sub
Public Property Location() As PointF
Get
Return _location
End Get
Set(ByVal value As PointF)
If value.X < _frame.X Then
value.X = _frame.X
ElseIf value.X > _frame.Right Then
value.X = _frame.Right
End If
If value.Y < _frame.Y Then
value.Y = _frame.Y
ElseIf value.Y > _frame.Bottom Then
value.Y = _frame.Bottom
End If
_location = value
End Set
End Property
Public Property Velocity() As PointF
Get
Return _velocity
End Get
Set(ByVal value As PointF)
_velocity = value
End Set
End Property
Public Property Frame() As RectangleF
Get
Return _frame
End Get
Set(ByVal value As RectangleF)
_frame = value
End Set
End Property
Public Sub [Next]()
_velocity = _velocity.Multiply(1.0! - _friction)
_location = PointF.Add(_location, New SizeF(_velocity))
End Sub
Public Sub MoveTowards(ByVal p As PointF, ByVal from As PointF)
p = New PointF(p.X - from.X, p.Y - from.Y)
_velocity = PointF.Add(_velocity.Multiply(0.7!), New SizeF(p.Multiply(0.3!))) '.Limit(5.0!)
End Sub
End Class
Public Class Spring
Private _defaultDistance As Double
Private _leniency As Double
Private _elasticity As Double
Private _point1, _point2 As Particle
Public Sub New()
_leniency = 1.0#
_elasticity = 0.2#
End Sub
Public Property DefaultDistance() As Double
Get
Return _defaultDistance
End Get
Set(ByVal value As Double)
_defaultDistance = value
End Set
End Property
Public Property Leniency() As Double
Get
Return _leniency
End Get
Set(ByVal value As Double)
_leniency = value
End Set
End Property
Public Property Elasticity() As Double
Get
Return _elasticity
End Get
Set(ByVal value As Double)
_elasticity = value
End Set
End Property
Public Property Point1() As Particle
Get
Return _point1
End Get
Set(ByVal value As Particle)
_point1 = value
End Set
End Property
Public Property Point2() As Particle
Get
Return _point2
End Get
Set(ByVal value As Particle)
_point2 = value
End Set
End Property
Public Sub [Next]()
Dim distance As Double = Point1.Location.DistanceTo(Point2.Location)
Dim difference As Double = _defaultDistance - distance
Dim p1 As New PointF(_point1.Location.X, _point1.Location.Y), _
p2 As New PointF(_point2.Location.X, _point2.Location.Y)
Dim dX As Single = (p1.X + p2.X) / 2.0!, _
dY As Single = (p1.Y + p2.Y) / 2.0!
p1.X -= dX
p2.X -= dX
p1.Y -= dY
p2.Y -= dY
If Math.Abs(difference) > _leniency Then
p1 = p1.Multiply(CSng((1.0# - difference / distance) * _elasticity))
p2 = p2.Multiply(CSng((1.0# - difference / distance) * _elasticity))
End If
_point1.Location = New PointF(p1.X + dX, p1.Y + dY)
_point2.Location = New PointF(p2.X + dX, p2.Y + dY)
End Sub
End Class
However, the cell ends up being squashed instead of being pushed back into a proper circle like it should. The way I set it up is:
Code:
Dim f As New RectangleF(-CSng(Game.Width / 2), -CSng(Game.Height / 2), Game.Width, Game.Height)
For i As Integer = 0 To 359
Dim x As Single = CSng(Math.Cos(i * Math.PI / 180) * 50), _
y As Single = CSng(Math.Sin(i * Math.PI / 180) * 50)
Dim p As New Spring.Particle()
p.Frame = f
p.Location = New PointF(x, y)
particles.Add(p)
Next
centerParticle = New Spring.Particle()
centerParticle.Frame = f
For i As Integer = 0 To 359
For j As Integer = i + 1 To 359
Dim s As New Spring.Spring()
s.Point1 = particles(i)
s.Point2 = particles(j)
s.DefaultDistance = particles(i).Location.DistanceTo(particles(j).Location)
springs.Add(s)
Next
Dim s2 As New Spring.Spring()
s2.Point1 = particles(i)
s2.Point2 = centerParticle
springs.Add(s2)
Next
Why doesn't it spring properly? How can I make this work?
Tags for this Thread
Posting Permissions
- You may not post new threads
- You may not post replies
- You may not post attachments
- You may not edit your posts
-
Forum Rules
|
Click Here to Expand Forum to Full Width
|