Ping Pong in Java Script

Viewed 91

I'm trying to figure out why Positions are returned NaN in browser. this game being rendered in loop and updated as soon as monitor ready to, that's defined in update() function an runs infinite. reset() function is a part of updating so it will randomly generate headings, also there is a while which corresponds to filtering little and boring movements.

Positions are consist of

  1. A direction which is an Array having x,y times..
  2. A Velocity which is constant during the whole game..
  3. Differ value constitute of time delta indicates how much milliseconds passed from last rendered frame to the new one

I appreciate your help.

//br.js

 

     const ausgebur_Velocity = .002
        class Ball {
            constructor(ballElement) {
                this.ballElement = ballElement
                this.reset()
            }
        
            get x() {
                return parseFloat(getComputedStyle(this.ballElement).getPropertyValue("--x"))
            }
        
            set x(value) {
                this.ballElement.style.setProperty("--x", value)
            }
        
            get y() {
                return parseFloat(getComputedStyle(this.ballElement).getPropertyValue("--y"))
            }
        
            set y(value) {
                this.ballElement.style.setProperty("--y", value)
            }
        
            reset() {
                this.x = 50;
                this.y = 50;
                this.direction = { x: 50, y: 25 }
        
                while (Math.abs(this.direction.x) <= .2 || Math.abs(this.direction.x >= .9)) {
                    const heading = randomNumberBet(0, 2 * Math.PI)
                    this.direction = { x: Math.cos(heading), y: Math.sin(heading) }
        
                }
                this.velocity = ausgebur_Velocity
            }
        
            update(differ) {
                this.x += this.direction.x * this.velocity * differ;
                this.y += this.direction.y * this.velocity * differ;
                console.log(this.x)
                console.log(this.y)
        
            }
        
        }
        
        function randomNumberBet(min, max) {
            return Math.random() * (max - min) + min
        }
        
        
        // Main Script Below
        const ball = new Ball(document.getElementById('ball'))
        
        let lastTime
        function update(time) {
            if (lastTime != null) {
                const differ = time - lastTime
        
                ball.update()
            }
            lastTime = time
        
            window.requestAnimationFrame(update)
        }
        
        window.requestAnimationFrame(update)
        
         
    //style.css
    
        *,
        *::after,
        *::before {
        box-sizing: border-box;
    }
    
    :root {
        --hue: 200;
        --saturation: 50%;
        --foreground: hsl(var(--hue), var(--saturation), 75%);
        --background: hsl(var(--hue), var(--saturation), 25%);
    }
    
    body {
        overflow: hidden;
        margin: 0;
        background-color: var(--background)
    }
    
    .control {
        --position: 50;
    
        position: absolute;
        background-color: var(--foreground);
        top: calc(var(--position)*1vh);
        transform: translateY(-50%);
        width: 1vh;
        height: 10vh;
    }
    
    #player_control {
        left: 1vw;
    }
    
    #pc_control {
        right: 1vw;
    }
    
    #ball {
        --x: 50;
        --y: 50;
    
        position: absolute;
        background-color: var(--foreground);
        left: calc(var(--x)*1vh);
        top: calc(var(--y)*1vh);
        transform: translate(-50%, -50%);
        width: 3vh;
        height: 3vh;
        border-radius: 50%;
    
    }
    
    .score {
        display: flex;
        justify-content: center;
        font-weight: bold;
        font-size: 7vh;
        color: var(--foreground);
    }
    
    .score>* {
        flex-grow: 1;
        flex-basis: 0%;
        padding: 0 2vh;
        margin: 1vh 0;
        opacity: .5;
    }
    
    .score>:first-child {
        text-align: right;
        border-right: .5vh solid var(--foreground);
    }

//ping.html

    <!DOCTYPE html>
    <html lang="en">
    
    <head>
        <meta charset="UTF-8">
        <meta http-equiv="X-UA-Compatible" content="IE=edge">
        <meta name="viewport" content="width=device-width, initial-scale=1.0">
        <link rel="stylesheet" href="/style.css">
        <script src="/br.js" type="module"></script>
        <title>PING</title>
    </head>
    
    <body>
        <div class="score">
            <div class="player_score">0</div>
            <div class="pc_score">0</div>
        </div>
    
        <div id="ball"></div>
        <div class="control" id="player_control"></div>
        <div class="control" id="pc_control"></div>
    </body>
    
    </html>
1 Answers

It seems the the problem is that get the coordonates from --x and --y css properties, which are not defined here.

Using top and left works slightly better but I think you'ill have to improve your algorithms.

const ausgebur_Velocity = .002
class Ball {
  constructor(ballElement) {
    this.ballElement = ballElement
    this.reset()
  }

  get x() {
    return parseFloat(getComputedStyle(this.ballElement).getPropertyValue("left"))
  }

  set x(value) {
    this.ballElement.style.setProperty("left", "" + value + "px")
  }

  get y() {
    return parseFloat(getComputedStyle(this.ballElement).getPropertyValue("top"))
  }

  set y(value) {
    this.ballElement.style.setProperty("top", "" + value + "px")
  }

  reset() {
    this.x = 50;
    this.y = 50;
    this.direction = {
      x: 50,
      y: 25
    }

    while (Math.abs(this.direction.x) <= .2 || Math.abs(this.direction.x >= .9)) {
      const heading = randomNumberBet(0, 2 * Math.PI)
      this.direction = {
        x: Math.cos(heading),
        y: Math.sin(heading)
      }

    }
    this.velocity = ausgebur_Velocity
  }

  update(differ) {
    this.x += this.direction.x * this.velocity * differ;
    this.y += this.direction.y * this.velocity * differ;
    console.log("x", this.x)
    console.log("y", this.y)

  }

}

function randomNumberBet(min, max) {
  return Math.random() * (max - min) + min
}


// Main Script Below
const ball = new Ball(document.getElementById('ball'))

let lastTime

function update(time) {
  if (lastTime != null) {
    const differ = time - lastTime
    ball.update(differ)
  }
  lastTime = time

  window.requestAnimationFrame(update)
}

window.requestAnimationFrame(update)
*,
*::after,
*::before {
  box-sizing: border-box;
}

 :root {
  --hue: 200;
  --saturation: 50%;
  --foreground: hsl(var(--hue), var(--saturation), 75%);
  --background: hsl(var(--hue), var(--saturation), 25%);
}

body {
  overflow: hidden;
  margin: 0;
  background-color: var(--background)
}

.control {
  --position: 50;
  position: absolute;
  background-color: var(--foreground);
  top: calc(var(--position)*1vh);
  transform: translateY(-50%);
  width: 1vh;
  height: 10vh;
}

#player_control {
  left: 1vw;
}

#pc_control {
  right: 1vw;
}

#ball {
  --x: 50;
  --y: 50;
  position: absolute;
  background-color: var(--foreground);
  left: calc(var(--x)*1vh);
  top: calc(var(--y)*1vh);
  transform: translate(-50%, -50%);
  width: 3vh;
  height: 3vh;
  border-radius: 50%;
}

.score {
  display: flex;
  justify-content: center;
  font-weight: bold;
  font-size: 7vh;
  color: var(--foreground);
}

.score>* {
  flex-grow: 1;
  flex-basis: 0%;
  padding: 0 2vh;
  margin: 1vh 0;
  opacity: .5;
}

.score>:first-child {
  text-align: right;
  border-right: .5vh solid var(--foreground);
}
<!DOCTYPE html>
<html lang="en">

<head>
  <meta charset="UTF-8">
  <meta http-equiv="X-UA-Compatible" content="IE=edge">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <link rel="stylesheet" href="/style.css">
  <script src="/br.js" type="module"></script>
  <title>PING</title>
</head>

<body>
  <div class="score">
    <div class="player_score">0</div>
    <div class="pc_score">0</div>
  </div>

  <div id="ball"></div>
  <div class="control" id="player_control"></div>
  <div class="control" id="pc_control"></div>
</body>

</html>

Related