JSFiddle - React, Tailwind, and code Playground

by Peter Johnson

HTML

<html>
    <head>
        <meta name="apple-mobile-web-app-capable" content="yes" />
        <meta name="apple-mobile-web-app-status-bar-style" content="black-translucent" />
        <style>
            
            html{
                width:100%;
                height:100%;
                margin:0;
                padding:0;
            }
            
            body{
                font-family:helvetica,arial,sans serif;
                width:100%;
                height:100%;
                margin:0;
                padding:0;
                background-color: #000;
                color: #fff;
            }
            
            .ball{
                position:absolute;
                width:48px;
                height:48px;
                border-radius:48px;
                -webkit-radius:48px;
                background-color:#efefef
            }
            
            ul {
                margin: 0;
                padding: 0;
                list-style: none;
            }
            
            span.acc {
                color: red;                    
            }
        </style>
    </head>
    <body>
        <div id="content">
            <ul>
                <li>accX: <span id="accelerationX" class="acc"></span> g</li>

                <li>accY: <span id="accelerationY" class="acc"></span> g</li>

                <li>accZ: <span id="accelerationZ" class="acc"></span> g</li>

                <li>rotAlpha: <span id="rotationAlpha" class="acc"></span> degrees</li>

                <li>rotBeta: <span id="rotationBeta" class="acc"></span> degrees</li>

                <li>rotGamma: <span id="rotationGamma" class="acc"></span> degrees</li>

            </ul>
        </div>
    </body>
</html>

CoffeeScript

class Ball

  constructor: (@element) ->

    @location = x: 0, y: 0
    @velocity = x: 0, y: 0
    @acceleration = x: 0, y: 0
    @boundary = x:0, y:0, width: Infinity, height: Infinity

  tick: (landscape=true) =>

    if landscape is true

      @velocity.x = @velocity.x + @acceleration.y
      @velocity.y = @velocity.y + @acceleration.x
    
    else

      @velocity.y = @velocity.y - @acceleration.y
      @velocity.x = @velocity.x + @acceleration.x

    @velocity.x = @velocity.x * 0.99
    @velocity.y = @velocity.y * 0.99

    @checkBoundary()

    @location.y = parseInt( @location.y + @velocity.y / 50 )
    @location.x = parseInt( @location.x + @velocity.x / 50 )

  checkBoundary: =>

    if @location.x < @boundary.x
      @location.x = @boundary.x
      @velocity.x = [email protected]/2

    if @location.y < @boundary.y
      @location.y = @boundary.y
      @velocity.y = [email protected]/2

    if @location.x > @boundary.width
      @location.x = @boundary.width
      @velocity.x = [email protected]/2

    if @location.y > @boundary.height
      @location.y = @boundary.height
      @velocity.y = [email protected]/2

  move: =>

    @element.style.top = @location.y + 'px' 
    @element.style.left = @location.x + 'px'

class Stage

  constructor: (@window) ->

    @balls = []

  tick: =>

    landscapeOrientation = ( @window.document.innerWidth / @window.document.innerHeight ) > 1

    for ball in @balls

      ball.tick(landscapeOrientation)
      ball.move()

  createBalls: (total,size=50) =>

    wid = if @window.innerWidth > 0 then window.innerWidth else screen.width
    hei = if @window.innerHeight > 0 then window.innerHeight else screen.height

    for i in [0...total]

      element = @window.document.createElement 'div'
      element.setAttribute 'class', 'ball'
      @window.document.body.appendChild element

      ball = new Ball element
      ball.boundary.width = wid - size
      ball.boundary.height = hei - size
      ball.location.x = Math.round( Math.random() *...