Improved ropes
This commit is contained in:
parent
845a7d3aba
commit
b360d93333
13
main.go
13
main.go
|
@ -32,20 +32,21 @@ func start() {
|
|||
w4.PALETTE[1] = 0x012824
|
||||
w4.PALETTE[2] = 0x265935
|
||||
w4.PALETTE[3] = 0xff4d6d
|
||||
player = &Player{
|
||||
Position: Vector{80, 80},
|
||||
Speed: Vector{},
|
||||
Gamepad: w4.GAMEPAD1,
|
||||
}
|
||||
for i := 0; i < 4; i++ {
|
||||
p, s := CreateRope(
|
||||
Vector{0, rand.Float64()*40 + float64(i*40)},
|
||||
Vector{160, rand.Float64()*40 + float64(i*40)},
|
||||
15,
|
||||
10,
|
||||
)
|
||||
points = append(points, p...)
|
||||
sticks = append(sticks, s...)
|
||||
}
|
||||
player = &Player{
|
||||
Position: Vector{80, 80},
|
||||
Speed: Vector{},
|
||||
Gamepad: w4.GAMEPAD1,
|
||||
StickGrabbed: sticks[rand.Intn(len(sticks)-1)],
|
||||
}
|
||||
}
|
||||
|
||||
//go:export update
|
||||
|
|
78
player.go
78
player.go
|
@ -1,13 +1,17 @@
|
|||
package main
|
||||
|
||||
import "cart/w4"
|
||||
import (
|
||||
"cart/w4"
|
||||
"math"
|
||||
)
|
||||
|
||||
type Player struct {
|
||||
Position Vector
|
||||
Speed Vector
|
||||
PointGrabbed *Point
|
||||
Position Vector
|
||||
Speed Vector
|
||||
//PointGrabbed *Point
|
||||
StickGrabbed *Stick
|
||||
StickOffset float64
|
||||
GrabTimeout uint
|
||||
Offset float64
|
||||
Gamepad *uint8
|
||||
}
|
||||
|
||||
|
@ -23,32 +27,74 @@ func (p *Player) Update() {
|
|||
p.Speed.X += 1
|
||||
}
|
||||
isJumping := *p.Gamepad&w4.BUTTON_DOWN == 0
|
||||
p.Speed.Y += gravity
|
||||
if p.PointGrabbed != nil {
|
||||
p.Speed.Y = math.Min(4, p.Speed.Y+gravity)
|
||||
if p.StickGrabbed != nil {
|
||||
p.Speed.Y = 0
|
||||
p.Position = p.PointGrabbed.Position
|
||||
// p.Position = p.PointGrabbed.Position
|
||||
if *p.Gamepad&w4.BUTTON_LEFT != 0 {
|
||||
p.StickOffset -= 0.1
|
||||
}
|
||||
if *p.Gamepad&w4.BUTTON_RIGHT != 0 {
|
||||
p.StickOffset += 0.1
|
||||
}
|
||||
if p.StickOffset < 0 {
|
||||
point := p.StickGrabbed.PointA
|
||||
if len(point.Sticks) == 1 {
|
||||
p.StickOffset = 0
|
||||
} else {
|
||||
p.StickGrabbed = point.Sticks[0]
|
||||
p.StickOffset += 1
|
||||
}
|
||||
}
|
||||
if p.StickOffset > 1 {
|
||||
point := p.StickGrabbed.PointB
|
||||
if len(point.Sticks) == 1 {
|
||||
p.StickOffset = 1
|
||||
} else {
|
||||
p.StickGrabbed = point.Sticks[1]
|
||||
p.StickOffset -= 1
|
||||
}
|
||||
}
|
||||
p.Position = p.StickGrabbed.GetPosition(p.StickOffset)
|
||||
if *p.Gamepad&w4.BUTTON_2 != 0 {
|
||||
p.GrabTimeout = 10
|
||||
if isJumping {
|
||||
p.GrabTimeout = 5
|
||||
p.Speed.Y = -4.5
|
||||
impulse := p.Speed.MulScalar(-1)
|
||||
p.StickGrabbed.PointA.Position.MoveVec(impulse)
|
||||
p.StickGrabbed.PointB.Position.MoveVec(impulse)
|
||||
}
|
||||
p.PointGrabbed = nil
|
||||
p.StickGrabbed = nil
|
||||
}
|
||||
} else {
|
||||
p.Position.Move(p.Speed.X, p.Speed.Y)
|
||||
if *p.Gamepad&w4.BUTTON_DOWN == 0 && p.GrabTimeout == 0 {
|
||||
distance := math.MaxFloat64
|
||||
var selectedPoint *Point
|
||||
for _, point := range points {
|
||||
diff := p.Position.Sub(point.Position)
|
||||
if diff.LenSquared() < 25 {
|
||||
// nearPoints = append(nearPoints, p)
|
||||
*w4.DRAW_COLORS = 0x44
|
||||
w4.Rect(int(point.Position.X), int(point.Position.Y), 3, 3)
|
||||
p.PointGrabbed = point
|
||||
point.PreviousPosition.Move(-p.Speed.X*2, -p.Speed.Y*2)
|
||||
break
|
||||
dSquared := diff.LenSquared()
|
||||
if dSquared < distance {
|
||||
distance = dSquared
|
||||
selectedPoint = point
|
||||
}
|
||||
}
|
||||
stickDistance := math.MaxFloat64
|
||||
var selectedStick *Stick
|
||||
for _, stick := range selectedPoint.Sticks {
|
||||
distance := stick.GetDistance(p.Position)
|
||||
if distance < stickDistance {
|
||||
stickDistance = distance
|
||||
selectedStick = stick
|
||||
}
|
||||
}
|
||||
if stickDistance < 4 {
|
||||
p.StickGrabbed = selectedStick
|
||||
p.StickOffset = selectedStick.GetOffset(p.Position)
|
||||
p.StickGrabbed.PointA.Position.MoveVec(p.Speed)
|
||||
p.StickGrabbed.PointB.Position.MoveVec(p.Speed)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
47
ropes.go
47
ropes.go
|
@ -3,7 +3,6 @@ package main
|
|||
import (
|
||||
"cart/w4"
|
||||
"math"
|
||||
"strconv"
|
||||
)
|
||||
|
||||
type Point struct {
|
||||
|
@ -11,6 +10,16 @@ type Point struct {
|
|||
PreviousPosition Vector
|
||||
IsLocked bool
|
||||
TimeOffset uint64
|
||||
Sticks []*Stick
|
||||
}
|
||||
|
||||
func (p *Point) AddStick(stick *Stick) *Point {
|
||||
p.Sticks = append(p.Sticks, stick)
|
||||
return p
|
||||
}
|
||||
|
||||
func (p *Point) GetMotion() Vector {
|
||||
return p.Position.Sub(p.PreviousPosition)
|
||||
}
|
||||
|
||||
func (p *Point) Draw() {
|
||||
|
@ -31,6 +40,39 @@ type Stick struct {
|
|||
Length float64
|
||||
}
|
||||
|
||||
func (s *Stick) GetVector() Vector {
|
||||
return s.PointB.Position.Sub(s.PointA.Position)
|
||||
}
|
||||
|
||||
func (s *Stick) GetDistance(point Vector) float64 {
|
||||
ab := s.GetVector()
|
||||
ap := point.Sub(s.PointA.Position)
|
||||
bp := point.Sub(s.PointB.Position)
|
||||
|
||||
abbp := (ab.X*bp.X + ab.Y*bp.Y)
|
||||
abap := (ab.X*ap.X + ab.Y*ap.Y)
|
||||
|
||||
if abbp > 0 {
|
||||
return bp.Len()
|
||||
} else if abap < 0 {
|
||||
return ap.Len()
|
||||
}
|
||||
mod := ab.Len()
|
||||
return math.Abs(ab.X*ap.Y-ab.Y*ab.X) / mod
|
||||
}
|
||||
|
||||
func (s *Stick) GetPosition(offset float64) Vector {
|
||||
diff := s.GetVector()
|
||||
return s.PointA.Position.Sum(diff.MulScalar(offset))
|
||||
}
|
||||
|
||||
func (s *Stick) GetOffset(p Vector) float64 {
|
||||
ab := s.GetVector()
|
||||
ap := p.Sub(s.PointA.Position)
|
||||
projection := ap.ProjectTo(ab)
|
||||
return projection.Len() / ab.Len()
|
||||
}
|
||||
|
||||
func (s *Stick) Draw() {
|
||||
*w4.DRAW_COLORS = 0x3
|
||||
w4.Line(int(s.PointA.Position.X), int(s.PointA.Position.Y),
|
||||
|
@ -90,12 +132,13 @@ func CreateRope(start Vector, end Vector, divisions int) ([]*Point, []*Stick) {
|
|||
diffX := pos.X - lastPoint.Position.X
|
||||
diffY := pos.Y - lastPoint.Position.Y
|
||||
len := math.Sqrt(diffX*diffX + diffY*diffY)
|
||||
w4.Trace("Length between points is " + strconv.FormatFloat(len, 'f', 3, 64))
|
||||
stick := Stick{
|
||||
PointA: lastPoint,
|
||||
PointB: &point,
|
||||
Length: len,
|
||||
}
|
||||
stick.PointA.AddStick(&stick)
|
||||
stick.PointB.AddStick(&stick)
|
||||
sticks = append(sticks, &stick)
|
||||
}
|
||||
points = append(points, &point)
|
||||
|
|
21
vectors.go
21
vectors.go
|
@ -10,6 +10,13 @@ type Vector struct {
|
|||
Y float64
|
||||
}
|
||||
|
||||
func Vec(x float64, y float64) Vector {
|
||||
return Vector{
|
||||
x,
|
||||
y,
|
||||
}
|
||||
}
|
||||
|
||||
func (v *Vector) String() string {
|
||||
return "(" + strconv.FormatFloat(v.X, 'f', 3, 64) + "; " + strconv.FormatFloat(v.Y, 'f', 3, 64) + ")"
|
||||
}
|
||||
|
@ -57,7 +64,21 @@ func (v *Vector) Normalized() Vector {
|
|||
return Vector{x, y}
|
||||
}
|
||||
|
||||
func (v *Vector) Dot(v2 Vector) float64 {
|
||||
return v.X*v2.X + v.Y*v2.Y
|
||||
}
|
||||
|
||||
func (v *Vector) ProjectTo(v2 Vector) Vector {
|
||||
abdot := v.Dot(v2)
|
||||
bbdot := v2.Dot(v2)
|
||||
return v2.MulScalar(abdot / bbdot)
|
||||
}
|
||||
|
||||
func (v *Vector) Move(x float64, y float64) {
|
||||
v.X += x
|
||||
v.Y += y
|
||||
}
|
||||
func (v *Vector) MoveVec(v2 Vector) {
|
||||
v.X += v2.X
|
||||
v.Y += v2.Y
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue