skip to Main Content

I’m trying to implement the method update. With the guidelines that I have, this method receives the pressed keyList and updates the car speed and angle depending on the pressed keys. It also moves the car and returns a literal object x and y properties, where x and y are the car x and y position.

Constants to use:

SPEED_DOWN = 1; // The amount of speed to reduce when the user brakes (key down pressed). If you hold the key down the speed could be negative
and the car goes in reverse.
SPEED_INERTIA = 0.8; // The amount of speed to reduce when the user is not accelerating or braking (no key down or key up pressed)
SPEED_LIMIT = 12; // The maximum speed of the car. It applies to positive (ahead) and negative (reverse) speeds.
SPEED_UP 2; // The amount of speed to increase when the user accelerates (key up pressed).
TURN_AMOUNT 6; // The amount of degrees to increase / reduce to the car angle direction (key left reduce degrees and ley right increase degrees).

About speed updates

  • If the UP key is pressed, it increases the speed based on the SPEED_UP value.
  • If the DOWN key is pressed, it decreases the speed based on the SPEED_DOWN value.
  • The speed never should be bigger than SPEED_LIMIT value (positive or negative).
  • If neither of the UP nor the DOWN keys are pressed, it decreases the speed based on the SPEED_INERTIA value.
    About angle updates
  • If the LEFT key is pressed, it reduces the angle based on the TURN_AMOUNT value. If the RIGHT key is pressed, it increases the angle based on the TURN_AMOUNT value.
    About car movement
    Use trigonometry to decompose the force vector in horizontal and vertical factors. This approach can be used:
const deltax = speed * Math.cos(angle);
const deltay = speed * Math.sin(angle);
class Trigonometry {

    static toDegrees(radians) {
        return radians * 180 / Math.PI;
    }

    static toRadians(degrees) {
        return degrees * Math.PI / 180;
    }
}

Deltax is the horizontal value that causes this speed at this angle, and deltay is the vertical value that causes this speed at this angle. Please note that speed and angle are generic names, they are not necessarily related to the exercise.

For now I tried the implementation below, where the movement of the car is handled in the update method.

class Car {
        #carDom;
        #speed = 0;
        #angle = 0;
    
        constructor(carDom) {
            this.#carDom = carDom;
        }
    
        reset() {
            this.#speed = 0;
            this.#angle = 0;
            this.#carDom.style.left = `${TRACK_SIZE / 2}px`;
            this.#carDom.style.top = `${TRACK_SIZE / 2}px`;
        }
    
        update(keyList) {
            const step = 1;
            const carStyle = window.getComputedStyle(this.#carDom);
            const left = parseInt(carStyle.getPropertyValue('left'));
            const top = parseInt(carStyle.getPropertyValue('top'));

            // Speed updates
            if (keyList.includes("ArrowUp")) {
                this.#speed += SPEED_UP;
            } else if (keyList.includes("ArrowDown")) {
                this.#speed -= SPEED_DOWN;
            } else {
                this.#speed *= SPEED_INERTIA;
            }

            // Limit speed
            if (this.#speed > SPEED_LIMIT) {
                this.#speed = SPEED_LIMIT;
            } else if (this.#speed < -SPEED_LIMIT) {
                this.#speed = -SPEED_LIMIT;
            }

            // Angle updates
            if (keyList.includes("ArrowLeft")) {
                this.#angle -= TURN_AMOUNT;
            } else if (keyList.includes("ArrowRight")) {
                this.#angle += TURN_AMOUNT;
            }

            // Car movement
            const rad = Trigonometry.toRadians(this.#angle);
            const deltax = this.#speed * Math.cos(rad);
            const deltay = this.#speed * Math.sin(rad);

            this.#carDom.style.left = (left + deltax * step) + "px";
            this.#carDom.style.top = (top + deltay * step) + "px";

            return {
                x: parseFloat(this.#carDom.style.left),
                y: parseFloat(this.#carDom.style.top)
            };
        }
} 

2

Answers


  1. update(keyList) {
    const step = 1;

    // Speed updates
    if (keyList.includes("ArrowUp")) {
        this.#speed += SPEED_UP;
    } else if (keyList.includes("ArrowDown")) {
        this.#speed -= SPEED_DOWN;
    } else {
        this.#speed *= SPEED_INERTIA;
    }
    
    // Limit speed
    if (this.#speed > SPEED_LIMIT) {
        this.#speed = SPEED_LIMIT;
    } else if (this.#speed < -SPEED_LIMIT) {
        this.#speed = -SPEED_LIMIT;
    }
    
    // Angle updates
    if (keyList.includes("ArrowLeft")) {
        this.#angle -= TURN_AMOUNT;
    } else if (keyList.includes("ArrowRight")) {
        this.#angle += TURN_AMOUNT;
    }
    
    // Calculate new position
    const rad = Trigonometry.toRadians(this.#angle);
    const deltax = this.#speed * Math.cos(rad);
    const deltay = this.#speed * Math.sin(rad);
    
    // Update position
    const left = parseFloat(this.#carDom.style.left) || TRACK_SIZE / 2;
    const top = parseFloat(this.#carDom.style.top) || TRACK_SIZE / 2;
    
    this.#carDom.style.left = (left + deltax * step) + "px";
    this.#carDom.style.top = (top + deltay * step) + "px";
    
    return {
        x: parseFloat(this.#carDom.style.left),
        y: parseFloat(this.#carDom.style.top)
    };
    

    }

    Login or Signup to reply.
  2. I have recently used the moving car to make my project:

    You can take reference from the method

     #moveCar() {
        if (this.control.up) {
            this.speed += this.acceleration;
        }
        if (this.control.down) {
            this.speed -= this.acceleration;
        }
        if (this.speed != 0) {
    
            const flip = this.speed > 0 ? 1 : -1;
            if (this.control.left) {
                this.angle += 0.03 * flip;
    
            }
            if (this.control.right) {
                this.angle -= 0.03 * flip;
            }
        }
    
        if (this.speed > this.maxSpeed) {
            this.speed = this.maxSpeed;
        }
        if (this.speed < -this.maxSpeed / 2) {
            this.speed = -this.maxSpeed / 2;
        }
        if (this.speed > 0) {
            this.speed -= this.friction;
        }
        if (this.speed < 0) {
            this.speed += this.friction;
        }
        if (Math.abs(this.speed) < this.friction) {
            this.speed = 0;
        }
    
        this.x -= Math.sin(this.angle) * this.speed;
        this.y -= Math.cos(this.angle) * this.speed;
    }
    
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search