Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

My script changes some values with what seems to be no reason

Tags:

javascript

So I've been working on a script that spawns bubbles at the mouse coordinates. It is a very basic script that calculates some things like a random opacity, random size, etc.

var transform = (function () { // This piece is to test whether transform should be prefixed or not
  var testEl = document.createElement('div')
  if (testEl.style.transform == null) {
    var vendors = ['Webkit', 'Moz', 'ms']
    for (var vendor in vendors) {
      if (testEl.style[ vendors[vendor] + 'Transform' ] !== undefined) {
        return vendors[vendor] + 'Transform'
      }
    }
  }
  return 'transform'
})()

var bubbles = {}
bubbles.chance = 0.08  // Chance for a bubble to spawn at mousemove
bubbles.delay = 50     // Should minimally be 10, otherwise the circles can't transition from small to big
bubbles.duration = 800
bubbles.minScale = 0.2 // The scale of the bubbles will be anywhere between 0.2 and 1 of the default size defined by the CSS
bubbles.minOpacity = 0.4
bubbles.maxOpacity = 0.7

document.getElementById('bubbles').addEventListener('mousemove', function (e) {
  if (Math.random() < bubbles.chance) {
    var $el = document.createElement('div')
    var size = Math.random() * (1 - bubbles.minScale) + bubbles.minScale
    var transition = Math.round(bubbles.duration * 0.9)

    $el.style.transition = transition + 'ms ease-in-out'
    $el.style.top = e.offsetY + 'px'  // Seems to undergo a modulo for some periods of time
    $el.style.left = e.offsetX + 'px' // This one too
    $el.style[transform] = 'translate(-50%, -50%) scale(0)'
    $el.style.opacity = Math.random() * (bubbles.maxOpacity - bubbles.minOpacity) + bubbles.minOpacity

    window.setTimeout(function () {
      $el.style[transform] = 'translate(-50%, -50%) scale(' + size + ')'
      window.setTimeout(function () {
        $el.style[transform] = 'translate(-50%, -50%) scale(0)'
        window.setTimeout(function () {
          $el.parentNode.removeChild($el)
        }, transition)
      }, transition + bubbles.duration)
    }, bubbles.delay)

    document.getElementById('bubbles').appendChild($el)
  }
})
html, body{height:100%}body{margin:0;background-color:#17C}

#bubbles{
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
  overflow: hidden;
}

#bubbles > div{
  position: absolute;
  width: 12vw;
  height: 12vw;
  border-radius: 50%;
  background-color: #FFF;
}
<div id="bubbles"></div>

Now, for some reason, some of the bubbles aren't placed at the right coordinates. The script is supposed to literally take e.offsetX and e.offsetY every time it spawns a new bubble, but it sometimes seems to apply a modulo to the values.

The reason I think some kind of modulo is applied, is because when you only move in a horizontal line, all the displaced bubbles will also form a horizontal line. The same goes for vertical.

The script is vanilla JavaScript and the piece where the error seems to occur is here:

$el.style.top = e.offsetY + 'px'
$el.style.left = e.offsetX + 'px'

One weird thing to also note, is that the displacement isn't just occurring for one bubble at a time, but for all bubbles within short periods of time.

The bug occurs in all major browsers.

All input is appreciated!

like image 793
Gust van de Wal Avatar asked Sep 16 '16 17:09

Gust van de Wal


People also ask

Why does my script keep crashing?

This happens when you have changed a variable in your inspector most of the time. the smartest thing to do would just be change the variables in your inspector so you don't have to constantly change your script. after you have changed all the variables to your liking then go to your script and set them there to be fixed.

Why won't the editor let me change the value of an object?

Make sure the editor is not in play mode when you do this, or it won't stick. It happens because after your object is constructed, unity overwrites any initial values in the code with values saved in the scene. Inspector Won't change the value every time you update the code. answers.unity.com/questions/621684/… This Might Help @YashVakil Thanks.

Why won't the Inspector change the value of an object?

It's more of a workaround. Make sure the editor is not in play mode when you do this, or it won't stick. It happens because after your object is constructed, unity overwrites any initial values in the code with values saved in the scene. Inspector Won't change the value every time you update the code. answers.unity.com/questions/621684/…

Why won't my script work in Unity?

If that happens and you have Edit->Preferences->Auto-refresh on. If the script is actually showing up in Unity updated but not working as expected to go to the GameObject where the script is attached and right click on the script component choosing the reset option. It will work.


2 Answers

it has nothing to do with modulo! the offsetX and offsetY is calculated from e.target which sometimes is the bubbles div BUT other times is the circle generated (since its nested inside) thats why you get a small offset from the mouse position to the circle, so the next circle gets little values.

in other words, the problem replicates whenever you mouse over the generated circles.

you can use clientX and clientY to get absolute values.

here is an updated fiddle: https://jsfiddle.net/dwhcoqzc/1/

additionally, you can use other methods, such as prevent bubbling with useCapture.

like image 26
Bamieh Avatar answered Nov 14 '22 21:11

Bamieh


I see why it's happening. If you happen to hover over a bubble instead of the blue background, it uses the bubble as reference for offsetX and Y. If it's a full page app, you could use e.clientX and e.clientY instead. Otherwise you need to listen only to the event if it's fired on #bubbles.

like image 185
Joseph Marikle Avatar answered Nov 14 '22 21:11

Joseph Marikle