Skip to content

Instantly share code, notes, and snippets.

class Car {
constructor(outerDi, innerDi, screenHt, screenWd, carDi, obsts) {
this.x =
0.5 * (screenWd - (innerDi + outerDi) / 2) + round(random() * 80) - 40; // Slight variation in starting x
this.y = screenHt / 2 - 5; // Right above the starting line
this.angle = -PI / 2; // Facing upward
//Dimensions for later usage
this.carDi = carDi;
<head>
<!-- Load in Tensorflow, P5, and our Car Class-->
<script src="https://cdn.jsdelivr.net/npm/@tensorflow/tfjs@2.0.0/dist/tf.min.js"></script>
<script
src="https://cdnjs.cloudflare.com/ajax/libs/p5.js/1.1.9/p5.min.js"
integrity="sha512-WIklPM6qPCIp6d3fSSr90j+1unQHUOoWDS4sdTiR8gxUTnyZ8S2Mr8e10sKKJ/bhJgpAa/qG068RDkg6fIlNFA=="
crossorigin="anonymous"
></script>
<script src="car.js"></script>
function startNewGen() {
totalFitness = endGen();
let newCarArr = []; // The next generation
mutationRate = mrateInput.value() // Pull mutation rate
//Get parent weights
let parentWeights = [];
cars.forEach((c) => {
parentWeights.push(c.copyWeights());
frameCount += 1;
// If 200 frames has passed plus a scaled of the highestScore, then start next generation
if (frameCount > 200 + topFitnessScore * 3) {
startNewGen();
frameCount = 0;
} else if (frameCount > 80) { // Check for inactivity after 80 frames
let stillActive = false;
// Make sure atleast one car has made progress without dying
cars.forEach((car) => {
if (car.fitness > 3 && car.dead == false) {
function startNewGen() {
totalFitness = endGen();
let newCarArr = []; // The next generation
//Get parent weights
let parentWeights = [];
cars.forEach((c) => {
parentWeights.push(c.copyWeights());
});
copyWeights() {
// Turn weights from Tensorformat to array format
const weights = this.model.getWeights(); // Pull weights
const weightCopies = [];
weights.forEach((wLayer) => {
let values = wLayer.dataSync(); // turn that layer from Tensor into array
weightCopies.push(values);
});
function endGen() {
let totalFitness = 0
bestOfGen = 0
// Calculate total fitness and find highest performing car
cars.forEach((car, ind) => {
car.dead = true
totalFitness += car.fitness
if(car.fitness > bestOfGen) {bestOfGen = car.fitness}
})
function selectRandParent(tFit) {
let randVal = tFit * random() // Random value between (0, tFit)
let count = 0 // Cumulitive Fitness
for(let i = 0; i < cars.length; i++) {
count += cars[i].fitness
if(randVal <= count) {
return i
}
}
cars.forEach((car) => {
//Draw car
//Draw Wheels
fill("black");
strokeWeight(0);
ellipse(
car.x + (carDi / 2) * cos(car.angle + PI / 4),
car.y + (carDi / 2) * sin(car.angle + PI / 4),
carDi / 2.5
setupModel() {
// Create a sequential neural network
this.model = tf.sequential();
let hidden1 = tf.layers.dense({
units: 8,
activation: "relu",
inputDim: 5,
});
let outputLayer = tf.layers.dense({
units: 4,