'I am trying to add an object to the end of an array inside said object
I have some code that creates a bunch of Creatures(cells) and they move around the screen and eat food. They all have an age variable so once they become a certain age they attempt to clone themselves but I don't have a complete understanding of how this should work or how to go about solving this problem and I have not been able to find something about it online.
It looks something like this -->
let cells = [];
class Cell {
reproduce() {
cells[cells.length] = new Cell();
}}
I do have an if statement that decides if it should reproduce or not depending on the amount of food it has so I don't hit the call stack max.
The problem's I've noticed are that the cell that created more cells move faster after each birth and I'm not sure as to why. I feel as though somehow the cell that created the other cells are connected in someway and I'm not sure how to fix this problem. My actual code project will be posted below, any suggestions would be greatly appreciated. It should also be noted that I am new to this website so any tips on how I could improve the way I ask or format my questions would be greatly appreciated. Thanks much to those that help.
class Creature {
constructor(lifeSpan, pos, ms, s, r, h) {
this.maxSpeed = ms;
this.speed = s;
this.radius = r;
this.fat = 0;
this.target = createVector(0,0);
this.acc = createVector(0,0);
this.vel = createVector(0,0);
this.pos = pos;
this.life = lifeSpan;
this.lifeSpan = lifeSpan;
this.hunger = h;
this.age = 0;
}
update(i) {
//test for death
if (this.lifeSpan <= 0 || this.hunger <= 0) {
this.die(i);
}
//reproduce
if (this.age/365 > 25 && this.hunger > 10000) {
this.reproduce();
}
//look for food
this.findFood();
//move to target
this.move();
//test for eating
this.eat();
//draw creature
this.draw();
}
die(i) {
console.log(this.age/365, creatures.length-1);
creatures.splice(i, 1);
}
reproduce() {
console.log('Made Child');
this.hunger -= 10000;
creatures[creatures.length] = new Creature(this.life, this.pos, this.maxSpeed, this.speed, this.radius, 1095);
}
findFood() {
let d = pow(10, 10);
for (let i = 0; i < food.length; i++) {
let newD = dist(this.pos.x, this.pos.y, food[i].pos.x, food[i].pos.y);
if (newD < d) {
this.target = food[i].pos;
d = newD;
}
}
}
move() {
this.acc = p5.Vector.sub(this.target, this.pos);
this.acc.setMag(this.speed);
this.vel.add(this.acc);
this.vel.y = constrain(this.vel.y, -this.maxSpeed, this.maxSpeed);
this.vel.x = constrain(this.vel.x, -this.maxSpeed, this.maxSpeed);
this.pos.add(this.vel);
this.lifeSpan--;
this.hunger--;
this.age++;
}
eat() {
let distance = dist(this.pos.x, this.pos.y, this.target.x, this.target.y);
if (distance < this.radius/2 - 2.5) {
this.hunger += 365;
this.r++;
}
}
draw() {
ellipse(this.pos.x, this.pos.y, this.radius);
}
}
class Food {
constructor() {
this.r = 5;
this.pos = createVector(round(random(this.r, width-this.r)),
round(random(this.r, height-this.r)));
}
update() {
//test if eaten
for (let i = 0; i < creatures.length; i++) {
let d = dist(creatures[i].pos.x, creatures[i].pos.y, this.pos.x, this.pos.y);
if (d < creatures[i].radius/2 - this.r/2) {
this.pos = createVector(random(this.r, width-this.r),
random(this.r, height-this.r));;
}
}
//draw food
ellipse(this.pos.x, this.pos.y, this.r);
}
}
let creatures = [];
let food = [];
let time = 0;
function setup() {
createCanvas(windowWidth, windowHeight);
for (let i = 0; i < 30; i++) {
let lifeSpan = round(random(18000, 32850));
let r = round(random(10, 30));
let y = round(random(r, height-r));
let x = round(random(r, width-r));
let pos = createVector(x, y);
let ms = round(random(1, 5));
let s = round(random(5, 20))/100;
let h = round(random(545, 2190));
creatures[i] = new Creature(lifeSpan, pos, ms, s, r, h);
food[i] = new Food();
}
}
function draw() {
background(50);
for (let i = 0; i < food.length; i++) {
food[i].update();
}
for (let i = creatures.length-1; i >= 0; i--) {
creatures[i].update(i);
}
time++;
}
Solution 1:[1]
I'm not 100% sure without seeing the vector class But. I believe you are passing the vector for pos in as a reference. try doing something like this when reproducing
deconstruct this.pos like so {...this.pos}
creatures[creatures.length] = new Creature(this.life, {...this.pos}, this.maxSpeed,this.speed, this.radius, 1095);
even better yet maybe just try creating a new vector from the x and y like this
creatures[creatures.length] = new Creature(this.life, createVector(this.pos.x,this.pos.y), this.maxSpeed,this.speed, this.radius, 1095);
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
Solution | Source |
---|---|
Solution 1 | Jamie337nichols |