Much nicer flocking simulation
This commit is contained in:
parent
faa2a7cc96
commit
06da955b21
|
@ -0,0 +1,107 @@
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"flag"
|
||||||
|
"git.openprivacy.ca/sarah/microworlds/core"
|
||||||
|
"git.openprivacy.ca/sarah/microworlds/experiments"
|
||||||
|
"github.com/faiface/pixel/pixelgl"
|
||||||
|
"github.com/foolusion/quadtree"
|
||||||
|
"image/color"
|
||||||
|
"math/rand"
|
||||||
|
"time"
|
||||||
|
)
|
||||||
|
|
||||||
|
var sniffDistance = flag.Int("sniffDistance", 3, "the distance a turtle can detect pheromone levels from")
|
||||||
|
|
||||||
|
var W = 1
|
||||||
|
var envmap = [][]int{
|
||||||
|
{W, W, W, W, W, W, W, W, W, W, W, W, W, W, W},
|
||||||
|
{W, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, W},
|
||||||
|
{W, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, W},
|
||||||
|
{W, 0, 0, 0, 0, 0, 0, 0, 0, W, 0, 0, 0, 0, W},
|
||||||
|
{W, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, W},
|
||||||
|
{W, 0, 0, 0, 0, 0, W, 0, 0, W, 0, 0, 0, 0, W},
|
||||||
|
{W, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, W},
|
||||||
|
{W, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, W},
|
||||||
|
{W, 0, 0, 0, 0, W, 0, 0, 0, 0, 0, 0, 0, 0, W},
|
||||||
|
{W, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, W},
|
||||||
|
{W, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, W},
|
||||||
|
{W, 0, 0, 0, 0, 0, 0, W, 0, 0, 0, 0, 0, 0, W},
|
||||||
|
{W, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, W},
|
||||||
|
{W, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, W},
|
||||||
|
{W, W, W, W, W, W, W, W, W, W, W, W, W, W, W},
|
||||||
|
}
|
||||||
|
|
||||||
|
type Bird struct {
|
||||||
|
}
|
||||||
|
|
||||||
|
func (sm *Bird) Setup(env *core.Environment, t *core.Turtle) {
|
||||||
|
t.SetColor(color.RGBA{100, 255, 10, 0})
|
||||||
|
t.SetHeading(rand.Intn(8 ))
|
||||||
|
}
|
||||||
|
|
||||||
|
var searchtree = quadtree.XY{4, 4}
|
||||||
|
|
||||||
|
func (sm *Bird) Run(env *core.Environment, t *core.Turtle) {
|
||||||
|
//t.Wiggle()
|
||||||
|
|
||||||
|
t.FollowAverageGradient(env, 50,0.1, "bird")
|
||||||
|
t.RejectGradient(env, 0, "bird")
|
||||||
|
|
||||||
|
if !t.Step(env) {
|
||||||
|
//t.TurnAround()
|
||||||
|
t.Wiggle()
|
||||||
|
t.Wiggle()
|
||||||
|
t.Wiggle()
|
||||||
|
}
|
||||||
|
|
||||||
|
x, y := t.Pos()
|
||||||
|
center := quadtree.NewXY(float64(x), float64(y))
|
||||||
|
neighbours := env.GetNearestNeighbours(quadtree.NewAABB(*center, searchtree), 3)
|
||||||
|
|
||||||
|
if len(neighbours) > 2 {
|
||||||
|
//t.SetHeading(avgHead % 8)
|
||||||
|
// t.Wiggle()
|
||||||
|
} else {
|
||||||
|
t.Wiggle()
|
||||||
|
}
|
||||||
|
|
||||||
|
t.Drop(env, 1, "bird")
|
||||||
|
}
|
||||||
|
|
||||||
|
func mainrun() {
|
||||||
|
experiment := new(experiments.Experiment)
|
||||||
|
experiment.InitializeExperiment()
|
||||||
|
t := new(core.Turtle)
|
||||||
|
t.SetColor(color.RGBA{255, 0, 0, 255})
|
||||||
|
experiment.InitEnvironment(func(environment *core.Environment) {
|
||||||
|
// Create 2 food piles
|
||||||
|
|
||||||
|
for x := 0; x < 300; x++ {
|
||||||
|
for y := 0; y < 300; y++ {
|
||||||
|
if envmap[y/20][x/20] == 1 {
|
||||||
|
//if ((x %20 < 10) && (y% 20<10)) || x < 30 || y < 30 || y > 270 || x > 270 || (x <100 && y>200) || ((x>150 && x < 300) && (y > 150 && y<175)) || ((x>150 && x < 180) && (y > 100 && y<175)){
|
||||||
|
environment.Occupy(t, x, y)
|
||||||
|
environment.PutValue(x,y)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
||||||
|
experiment.InitNTurtles(func() core.Actor {
|
||||||
|
sm := new(Bird)
|
||||||
|
|
||||||
|
return sm
|
||||||
|
},1000)
|
||||||
|
|
||||||
|
experiment.InitPheromone("bird", color.RGBA{0x80, 0xaa, 0x00, 0x00})
|
||||||
|
experiment.OnStep = func(environment *core.Environment, turtles []*core.Turtle, i int) {
|
||||||
|
environment.EvaporateAndDiffuse(0.90, "bird")
|
||||||
|
}
|
||||||
|
experiment.Run()
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
rand.Seed(time.Now().UnixNano())
|
||||||
|
pixelgl.Run(mainrun)
|
||||||
|
}
|
|
@ -1,66 +0,0 @@
|
||||||
package main
|
|
||||||
|
|
||||||
import (
|
|
||||||
"flag"
|
|
||||||
"git.openprivacy.ca/sarah/microworlds/core"
|
|
||||||
"git.openprivacy.ca/sarah/microworlds/experiments"
|
|
||||||
"github.com/faiface/pixel/pixelgl"
|
|
||||||
"image/color"
|
|
||||||
)
|
|
||||||
|
|
||||||
var sniffDistance = flag.Int("sniffDistance", 3, "the distance a turtle can detect pheromone levels from")
|
|
||||||
|
|
||||||
type Bird struct {
|
|
||||||
}
|
|
||||||
|
|
||||||
func (sm *Bird) Setup(env *core.Environment, t *core.Turtle) {
|
|
||||||
t.SetColor(color.RGBA{100, 255, 10, 0})
|
|
||||||
//t.SetHeading(5)
|
|
||||||
}
|
|
||||||
|
|
||||||
func (sm *Bird) Run(env *core.Environment, t *core.Turtle) {
|
|
||||||
//t.Wiggle()
|
|
||||||
if t.AmountAll(env, 1, "bird") > 1 {
|
|
||||||
//t.Wiggle()
|
|
||||||
t.AvoidAverageGradient(env, 1, 2.5, "bird")
|
|
||||||
//t.Wiggle()
|
|
||||||
t.Step(env)
|
|
||||||
t.Drop(env, 2, "bird")
|
|
||||||
} else if t.AmountAll(env, 1, "bird") > 2 {
|
|
||||||
t.AvoidAverageGradient(env, 1, 1, "bird")
|
|
||||||
t.Wiggle()
|
|
||||||
t.Step(env)
|
|
||||||
t.Drop(env, 1, "bird")
|
|
||||||
} else {
|
|
||||||
// t.TurnAround()
|
|
||||||
// t.Wiggle()
|
|
||||||
// t.Wiggle()
|
|
||||||
// t.Wiggle()
|
|
||||||
t.FollowAverageGradient(env, 5, 1, "bird")
|
|
||||||
t.FollowAverageGradient(env, 4, 2, "bird")
|
|
||||||
t.FollowAverageGradient(env, 3, 3, "bird")
|
|
||||||
//t.FollowAverageGradient(env, 2, 4, "bird")
|
|
||||||
|
|
||||||
t.Step(env)
|
|
||||||
t.Drop(env, 1, "bird")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func mainrun() {
|
|
||||||
experiment := new(experiments.Experiment)
|
|
||||||
experiment.InitializeExperiment()
|
|
||||||
experiment.InitTurtles(func() core.Actor {
|
|
||||||
sm := new(Bird)
|
|
||||||
|
|
||||||
return sm
|
|
||||||
})
|
|
||||||
experiment.InitPheromone("bird", color.RGBA{0x80, 0xaa, 0x00, 0x00})
|
|
||||||
experiment.OnStep = func(environment *core.Environment, turtles []*core.Turtle, i int) {
|
|
||||||
environment.EvaporateAndDiffuse(0.99, "bird")
|
|
||||||
}
|
|
||||||
experiment.Run()
|
|
||||||
}
|
|
||||||
|
|
||||||
func main() {
|
|
||||||
pixelgl.Run(mainrun)
|
|
||||||
}
|
|
|
@ -149,24 +149,23 @@ func mainrun() {
|
||||||
}
|
}
|
||||||
|
|
||||||
x = append(x, float64(environment.Step))
|
x = append(x, float64(environment.Step))
|
||||||
prey = append(prey, float64(preyalive))
|
prey = append(prey, 100*(float64(preyalive)/float64(environment.Width()*environment.Height())))
|
||||||
pred = append(pred, float64(predalive))
|
pred = append(pred, 100*(float64(predalive)/float64(environment.Width()*environment.Height())))
|
||||||
|
|
||||||
preypop := chart.ContinuousSeries{
|
preypop := chart.ContinuousSeries{
|
||||||
Name: "Prey Population Size",
|
Name: "Prey Population Density",
|
||||||
XValues: x,
|
XValues: x,
|
||||||
YValues: prey,
|
YValues: prey,
|
||||||
}
|
}
|
||||||
|
|
||||||
predpop := chart.ContinuousSeries{
|
predpop := chart.ContinuousSeries{
|
||||||
Name: "Predator Population Size",
|
Name: "Predator Population Density",
|
||||||
XValues: x,
|
XValues: x,
|
||||||
YValues: pred,
|
YValues: pred,
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
graph := chart.Chart{
|
graph := chart.Chart{
|
||||||
Width: 300,
|
|
||||||
Height: 300,
|
|
||||||
|
|
||||||
Background: chart.Style{
|
Background: chart.Style{
|
||||||
Padding: chart.Box{
|
Padding: chart.Box{
|
||||||
|
@ -176,7 +175,7 @@ func mainrun() {
|
||||||
XAxis: chart.XAxis{Name: "Time Step", NameStyle: chart.Style{Show: true}, Style: chart.Style{Show: true}, ValueFormatter: func(v interface{}) string {
|
XAxis: chart.XAxis{Name: "Time Step", NameStyle: chart.Style{Show: true}, Style: chart.Style{Show: true}, ValueFormatter: func(v interface{}) string {
|
||||||
return fmt.Sprintf("%d", int(v.(float64)))
|
return fmt.Sprintf("%d", int(v.(float64)))
|
||||||
}},
|
}},
|
||||||
YAxis: chart.YAxis{Name: "Population", NameStyle: chart.Style{Show: true}, Style: chart.Style{Show: true}, ValueFormatter: func(v interface{}) string {
|
YAxis: chart.YAxis{Name: "Population", NameStyle: chart.Style{Show: true}, Style: chart.Style{Show: true,}, ValueFormatter: func(v interface{}) string {
|
||||||
return fmt.Sprintf("%d", int(v.(float64)))
|
return fmt.Sprintf("%d", int(v.(float64)))
|
||||||
}},
|
}},
|
||||||
Series: []chart.Series{
|
Series: []chart.Series{
|
||||||
|
|
|
@ -57,12 +57,12 @@ func (g *Graphics) ColorPheromone(name string, color [4]uint8) {
|
||||||
|
|
||||||
func (g *Graphics) Render(env *core.Environment, turtles []*core.Turtle) {
|
func (g *Graphics) Render(env *core.Environment, turtles []*core.Turtle) {
|
||||||
g.imd.Clear()
|
g.imd.Clear()
|
||||||
//g.window.Clear(color.RGBA{0,0,0,0})
|
g.window.Clear(color.RGBA{0,0,0,0})
|
||||||
pheromoneImage := image.NewRGBA(image.Rect(0, 0, int(g.width), int(g.height)))
|
pheromoneImage := image.NewRGBA(image.Rect(0, 0, int(g.width), int(g.height)))
|
||||||
for x := 0; x < int(g.width); x++ {
|
for x := 0; x < int(g.width); x++ {
|
||||||
for y := 0; y < int(g.height); y++ {
|
for y := 0; y < int(g.height); y++ {
|
||||||
if env.HasValue(x, y) {
|
if env.HasValue(x, y) {
|
||||||
g.DrawTileColor(g.imd, int32(x), int32(y), color.RGBA{255, 255, 255, uint8(255)})
|
pheromoneImage.SetRGBA(x,y, color.RGBA{255, 0, 128, 0xFF})
|
||||||
} else {
|
} else {
|
||||||
scaledamountRedTotal := 0
|
scaledamountRedTotal := 0
|
||||||
scaledamountGreenTotal := 0
|
scaledamountGreenTotal := 0
|
||||||
|
|
Loading…
Reference in New Issue