Why does my css-animation extend beyond the window? - javascript

I have made a CSS-animation with Velocity.js:
https://codepen.io/blaustern_fotografie/pen/GvxWoW
The code is designed such that the circles are not allowed to go beyond the window on the left and right side. The function "my_animate" is responsible for this:
function my_animate(circle) {
var new_y = Math.floor(
Math.random() * ((height -50)-50)+50
);
var new_x = Math.floor(
Math.random() * ((width-50)-50)+50
);
var r = Math.random();
//var nd = Math.floor(r * 500 - 250);
$(circle).velocity(
{
translateX: new_x-$(circle).position().left,
translateY: new_y-$(circle).position().top,
//translateZ: nd,
opacity: r,
blur: Math.round((1 - r) * 5)
},
{
duration: Math.round(Math.random() * 10000 + 10000),
complete: function() {
my_animate(circle);
}
}
);
}
Does anyone know why the circles are passing the edges?

Problem seems here in calculating the new position.
The use of Math.random() is leading to random values being generated for new_x.
var new_x = Math.floor(
Math.random() * ((width -50)-50)+50
);
Then new_x-$(circle).position().left is leading to values being generated which are out of window range.
You should normalise your randomiser to generate new position such that the values generated are always between the min and max points on the viewport.

You need to make the Math.random in range of your window.width, otherwise the randomizer will just calculate values out of your window.width.

Related

How can i make the enemy go to the character position?

What my game has is a character in a preset position in a 2d-game mobile(x=0.33, y=9.48, z=0). I have enemys that are spawn from different angles of the screen with a movement script. But i have to modify the script so it moves towards the character position always.
Tried to set the position of the enemy = with character position. but that doesnt work.
Anyone has any idea how can i do that?
here is the script:
///
//Speed - essential : true ?
let speed;
let enabled = false;
let phys;
function init() {
speed =4;
//let d = Math.sqrt( Math.pow((enemy.x-playerPos.x), 2) + Math.pow((enemy.y-playerPos.y), 2) );
}
function update(dt) {
dt = 1 / 60.0; // fixed delta time
let enemy = this.entity().position();
let player = this.scene().find('Actor')[0];
let playerPos = player.worldPosition();
let d = new Vec3(
playerPos.x - enemy.x,
playerPos.y - enemy.y,
playerPos.z - enemy.z
)
const length = Math.sqrt(d.x * d.x + d.y * d.y);
let dirTowardsPlayer = new Vec3 (
d.x / length,
d.y / length,
d.z / length
)
this.entity().setPosition(
dt * dirTowardsPlayer.x * speed,
dt * dirTowardsPlayer.y * speed,
dt * dirTowardsPlayer.z * speed);
log(dirTowardsPlayer)
}
function signal(name, value) {
enabled = value;
}
i am expecting the enemy to move towards the character preseted position

HTML5 Canvas : Spawn randomly positioned objects outside of the canvas

What I am trying to learn is how to spawn objects outside of the canvas from various directions...that is left, right, top, bottom.
For (i = 0; i < 10; i++) {
ctx.beginPath();
ctx.arc(Math.random()*Window.outerWidth, Math.random()*Window.outerHeight 30, 0, 2 * Math.PI, false);
ctx.fillStyle = 'black';
ctx.fill();
ctx.closePath();
}
So basically imagine objects appearing from some random positions at the top, left, right and botton edges of the canvas screen. Maybe even the corners. So the point is im having some issues with understanding the logic behind how this works. How do I achieve something like that?
Please bear in mind that I am not just looking for answers but a resource for learning. If you answer then please do so with teaching in mind and not 'points'.
This Math.random() * Window.outerWidth is fast write of :
var min = 0, max = Window.outerWidth;
Math.random() * (max - min + 1) + min;
To understand it, look this function :
function getRandom(min, max) { //You get number between [min, max]
return Math.floor(Math.random() * (max - min + 1)) + min;
}
If you want to add circle inside canvas, you need to set :
var min = 0,
max = Window.outerWidth;
Your code remove min variable. You get :
Math.random() * (max - 0) + 0; // replace min by 0
Math.random() * max // remove 0
Math.random() * Window.outerWidth // max = Window.outerWidth
You get : Math.random() * Window.outerWidth.
Links :
Generating random whole numbers in JavaScript in a specific range?

find position of a point with origin, angle and radius

im stuck with a trigonometry problem in a javascript game im trying to make.
with a origin point(xa,ya) a radius and destination point (ya,yb) I need to find the position of a new point.
//calculate a angle in degree
function angle(xa, ya, xb, yb)
{
var a= Math.atan2(yb - ya, xb - xa);
a*= 180 / Math.PI;
return a;
}
function FindNewPointPosition()
{
//radius origine(xa,xb) destination(ya,yb)
var radius=30;
var a = angle(xa, xb, ya, yb);
newpoint.x = xa + radius * Math.cos(a);
newpoint.y = ya + radius * Math.sin(a);
return newpoint;
}
Imagine a image because I dont have enough reputation to post one :
blue square is the map (5000x5000), black square (500x500) what players see (hud).
Cross(400,400) is the origin and sun(4200,4200) the destination.
The red dot (?,?) indicate to player which direction take to find the sun ..
But sun and cross position can be reverse or in different corner or anywhere !
At the moment the red dot do not do that at all ..
Tks for your help.
Why did you use ATAN2? Change to Math.atan() - you will get angle in var A
Where you have to place your red dot? inside hud?
Corrected code
https://jsfiddle.net/ka9xr07j/embedded/result/
var obj = FindNewPointPosition(400,4200,400,4200); - new position 417. 425
Finally I find a solution without using angle.
function newpointposition(origin, destination)
{
// radius distance between cross and red dot
var r=30;
// calculate a vector
var xDistance = destination.x - origin.x;
var yDistance = destination.y - origin.y;
// normalize vector
var length = Math.sqrt(xDistance * xDistance + yDistance * yDistance);
xDistance /= length;
yDistance /= length;
// add the radius
xDistance = xDistance * r;
yDistance = yDistance * r;
var newpoint = { x: 0, y: 0 };
newpoint.x = origin.x + xDistance;
newpoint.y = origin.y + yDistance;
return newpoint;
}
var radar = newpointposition({
x: 500,
y: 800
}, {
x: 3600,
y: 2850
});
alert(radar.x + ' ' + radar.y);
ty Trike, using jsfiddle really help me.

Canvas jitters half my rendering

I was working on a fun project that implicates creating "imperfect" circles by drawing them with lines and animate their points to generate a pleasing effect.
The points should alternate between moving away and closer to the center of the circle, to illustrate:
I think I was able to accomplish that, the problem is when I try to render it in a canvas half the render jitters like crazy, you can see it in this demo.
You can see how it renders for me in this video. If you pay close attention the bottom right half of the render runs smoothly while the top left just..doesn't.
This is how I create the points:
for (var i = 0; i < q; i++) {
var a = toRad(aDiv * i);
var e = rand(this.e, 1);
var x = Math.cos(a) * (this.r * e) + this.x;
var y = Math.sin(a) * (this.r * e) + this.y;
this.points.push({
x: x,
y: y,
initX: x,
initY: y,
reverseX: false,
reverseY: false,
finalX: x + 5 * Math.cos(a),
finalY: y + 5 * Math.sin(a)
});
}
Each point in the imperfect circle is calculated using an angle and a random distance that it's not particularly relevant (it relies on a few parameters).
I think it's starts to mess up when I assign the final values (finalX,finalY), the animation is supposed to alternate between those and their initial values, but only half of the render accomplishes it.
Is the math wrong? Is the code wrong? Or is it just that my computer can't handle the rendering?
I can't figure it out, thanks in advance!
Is the math wrong? Is the code wrong? Or is it just that my computer can't handle the rendering?
I Think that your animation function has not care about the elapsed time. Simply the animation occurs very fast. The number of requestAnimationFrame callbacks is usually 60 times per second, So Happens just what is expected to happen.
I made some fixes in this fiddle. This animate function take care about timestamp. Also I made a gradient in the animation to alternate between their final and initial positions smoothly.
ImperfectCircle.prototype.animate = function (timestamp) {
var factor = 4;
var stepTime = 400;
for (var i = 0, l = this.points.length; i < l; i++) {
var point = this.points[i];
var direction = Math.floor(timestamp/stepTime)%2;
var stepProgress = timestamp % stepTime * 100 / stepTime;
stepProgress = (direction == 0 ? stepProgress: 100 -stepProgress);
point.x = point.initX + (Math.cos(point.angle) * stepProgress/100 * factor);
point.y = point.initY + (Math.sin(point.angle) * stepProgress/100 * factor);
}
}
Step by Step:
based on comments
// 1. Calculates the steps as int: Math.floor(timestamp/stepTime)
// 2. Modulo to know if even step or odd step: %2
var direction = Math.floor(timestamp/stepTime)%2;
// 1. Calculates the step progress: timestamp % stepTime
// 2. Convert it to a percentage: * 100 / stepTime
var stepProgress = timestamp % stepTime * 100 / stepTime;
// if odd invert the percentage.
stepProgress = (direction == 0 ? stepProgress: 100 -stepProgress);
// recompute position based on step percentage
// factor is for fine adjustment.
point.x = point.initX + (Math.cos(point.angle) * stepProgress/100 * factor);
point.y = point.initY + (Math.sin(point.angle) * stepProgress/100 * factor);

Possible to detect collisions of Paths or Kinetic Blobs/Layers?

I have multiple layers on my stage. Each layer contains images surrounded with a blub ( see this question). Each blub is draggable.
Is it possible to detect collisions between the blubs while moving them?
I don't want to have overlapping bubbles, but rather if they collide, they should melt.
You can determine if blobs are colliding.
There are at least 2 methods:
calculate the bounding box for all blobs and test if the bounding boxes collide.
draw each blob on a separate offscreen canvas and use pixel testing to see if they collide.
The bounding box method is faster.
The pixel-testing method is more precise, but slower are requires many more resources.
An example:
Here's how to calculate and test if 2 blob bounding boxes are colliding.
A Demo: http://jsfiddle.net/m1erickson/9tB7d/
Start with a Kinetic Blob
var blueBlob = new Kinetic.Line({
points: [73,140,340,23,500,109,300,170],
stroke: 'blue',
strokeWidth: 10,
fill: '#aaf',
tension: 0.8,
closed: true
});
That blob is made up of a set of Bezier curves.
Get the Bezier curves that make up the blob:
function kineticBlob2Beziers(blob){
var beziers=[];
var start=blob.getPoints();
var pts=blob.getTensionPoints();
var n=0;
var lastN=pts.length-2;
var sx=start[0];
var sy=start[1];
while(n<lastN){
bez={
s: {x:sx,y:sy},
c1:{x:pts[n++],y:pts[n++]},
c2:{x:pts[n++],y:pts[n++]},
e: {x:pts[n++],y:pts[n++]}
};
beziers.push(bez);
sx=pts[n-2];
sy=pts[n-1];
}
return(beziers);
}
Calculate the blobs bounding box using its Bezier curves:
function getBlobBB(beziers){
var minX=1000000;
var minY=1000000;
var maxX=-1000000;
var maxY=-1000000;
for(var i=0;i<beziers.length;i++){
var bez=beziers[i];
for(var t=0.00;t<=1.00;t+=.01){
var pt=getCubicBezierXYatT(bez.s,bez.c1,bez.c2,bez.e,t);
if(pt.x<minX){minX=pt.x;}
if(pt.x>maxX){maxX=pt.x;}
if(pt.y<minY){minY=pt.y;}
if(pt.y>maxY){maxY=pt.y;}
}
}
return({x:minX,y:minY,width:maxX-minX,height:maxY-minY});
}
function getCubicBezierXYatT(startPt,controlPt1,controlPt2,endPt,T){
var x=CubicN(T,startPt.x,controlPt1.x,controlPt2.x,endPt.x);
var y=CubicN(T,startPt.y,controlPt1.y,controlPt2.y,endPt.y);
return({x:x,y:y});
}
// cubic helper formula at T distance
function CubicN(T, a,b,c,d) {
var t2 = T * T;
var t3 = t2 * T;
return a + (-a * 3 + T * (3 * a - a * T)) * T
+ (3 * b + T * (-6 * b + b * 3 * T)) * T
+ (c * 3 - c * 3 * T) * t2
+ d * t3;
}
Determines if 2 bounding boxes (rectangles) are colliding:
function Colliding(left1,top1,right1,bottom1,left2,top2,right2,bottom2){
return(!(
left1 > right2 ||
right1 < left2 ||
bottom1 < top2 ||
top1 >bottom2
));
}

Categories

Resources