Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/379.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/html/75.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript 球在4-5秒后停止反弹_Javascript_Html_Css_Canvas - Fatal编程技术网

Javascript 球在4-5秒后停止反弹

Javascript 球在4-5秒后停止反弹,javascript,html,css,canvas,Javascript,Html,Css,Canvas,下面是javascript: var canvas=document.getElementById('canvas'), ctx=canvas.getContext('2d'), ax=50, ay=50, avx=5, avy=2, 半径=50; canvas.width=window.innerWidth; canvas.height=window.innerHeight; 函数drawArc(){ ctx.beginPath(); ctx.fillStyle=“白色”; ctx.弧(ax

下面是javascript:

var canvas=document.getElementById('canvas'),
ctx=canvas.getContext('2d'),
ax=50,
ay=50,
avx=5,
avy=2,
半径=50;
canvas.width=window.innerWidth;
canvas.height=window.innerHeight;
函数drawArc(){
ctx.beginPath();
ctx.fillStyle=“白色”;
ctx.弧(ax,ay,半径,0,2*Math.PI);
ctx.fill();
ctx.closePath();
};
函数更新(){
clearRect(0,0,canvas.width,canvas.height);
drawArc();
ax+=avx;
ay-=avy;
avy-=0.2;
如果(ay+半径>=画布高度){
平均值*=-0.8;
avx*=0.9;
};
如果(轴+半径>=画布宽度){
avx=-avx;
};

如果(ax-radius我想你想要这个:

var canvas=document.getElementById('canvas'),
ctx=canvas.getContext('2d'),
ax=50,
ay=50,
avx=5,
avy=2,
半径=50;
canvas.width=window.innerWidth;
canvas.height=window.innerHeight;
函数drawArc(){
ctx.beginPath();
ctx.fillStyle=“白色”;
ctx.弧(ax,ay,半径,0,2*Math.PI);
ctx.fill();
ctx.closePath();
};
var-hitTheGround=0;
函数更新(){
clearRect(0,0,canvas.width,canvas.height);
drawArc();
ax+=avx;
ay-=avy;
avy-=0.2;
如果(ay+半径>=画布高度){
平均值*=-0.8;
avx*=0.9;
}
如果(轴+半径>=画布宽度){
avx=-avx;
}
如果(ax-radius=canvas.height-3){
打地面++;
}
否则{
接地=0;
}
if(hitTheGround==100){//如果它在地面附近跳得太频繁
返回setTimeout(函数(){clearInterval(interval)},1000);
}
}
var interval=setInterval(更新,10);
body,html{
保证金:0;
填充:0;
}
#帆布{
背景色:黑色;
}

简单的回答是,由于你没有将球移离地面,所以你会受到很多打击。下一帧球仍在撞击地面,当你降低它的速度时,它只是停滞不前

在小提琴的第29行后面加上这个

ay = canvas.height - radius;

好的,首先,是有效的代码

<html>
  <head>
    <style>
body, html {
  margin: 0;
  padding: 0;
}
#canvas {
  background-color: black;
}
    </style>
    <script>
function drawArc() {
  ctx.beginPath();
  ctx.fillStyle = "white";
  ctx.arc(ax, ay, radius, 0, 2 * Math.PI);
  ctx.fill();
  ctx.closePath();
};

function update() {
  ctx.clearRect(0, 0, canvas.width, canvas.height);
  drawArc();
  ax += avx;
  ay -= avy;
  avy -= 0.2;

  if (ay + radius >= canvas.height) {
    avy *= -0.8;
    avx *= 0.9;
  };

  if (ax + radius >= canvas.width) {
    avx = -avx;
  };

  if (ax - radius <= 0) {
    avx = -avx;
  };
}

function onload()
{
canvas = document.getElementById('canvas');
ctx = canvas.getContext('2d');
ax = 50;
ay = 50;
avx = 5;
avy = 2;
radius = 50;

canvas.width = window.innerWidth;
canvas.height = window.innerHeight;
setInterval(update, 10);
}
    </script>
    <style>
    </style>
  </head>
  <body onload="onload()">
    <canvas id="canvas"></canvas>
  </body>
</html>
然而,这会产生另一个问题。你正在使用的代码需要阻尼,或者每次反弹时球都反弹得更高。这是因为你在这条线上加速并获得能量

avy -= 0.2;
您的另一个答案建议您减少阻尼,但不要通过更改这一行来完全消除阻尼。您必须调整这一行,使其具有您想要的行为

avy *= -0.8;//-0.8 is too little? -1 is too much
最后一次编辑,我保证。我确实从中得到了很多乐趣。这个问题并不是那么简单,你可以用psuedo物理来很好地模拟一个球的反弹。即使你把所有正确的方程都放进去,你仍然会得到一个小的永久反弹,因为这是现实生活中发生的事情。当球移动得足够慢并且其他力(不是重力,而是强、弱和电磁引力)足够靠近地板控制并使球停止移动。因此,我又打了一次球,大大改善了物理性能。这并不完美,但在某些时候你必须问,模拟的逼真度是否比平滑行为更重要,以匹配我想要看到的。希望这能有所帮助

<html>
  <head>
    <style>
body, html {
  margin: 0;
  padding: 0;
}
#canvas {
  background-color: black;
}
    </style>
    <script>
function drawArc() {
  ctx.beginPath();
  ctx.fillStyle = "white";
  ctx.arc(xPos, yPos, radius, 0, 2 * Math.PI);
  ctx.fill();
  ctx.closePath();
};

function update() {
  ctx.clearRect(0, 0, canvas.width, canvas.height);
  drawArc();
  var dx = xVel*timeStep;
  var dy = yVel*timeStep;

  if(yVel<radius && yVel>-radius && canvas.height-(yPos+radius) < .1)
  {
    yVel = 0;
    yPos = canvas.height-radius;
    dy=0;

    //friction affects xVel
    xVel *= fFloor;
  }
  else if (yPos + dy + radius >= canvas.height) {
    //you will be below the floor; there is a bounce

    //find the rest of the falling interval
    var remainingY = canvas.height-(yPos+radius);

    //find the rest of the time step    
    var remainingTime = remainingY / yVel;

    //add acceleration for that time
    yVel += gravity * remainingTime

    //friction affects xVel
    xVel *= fFloor;

    //elasticity affects yVel
    yVel *= eFloor;

    //now you are bouncing up
    //what is time up
    remainingTime = timeStep - remainingTime;

    //set final position
    yPos = canvas.height + (yVel*remainingTime) - radius;

    //add acceleration for that time
    yVel += gravity * remainingTime;
  }

  else
  {
    //do not hit the floor, falling the whole time
    yPos += dy;
    yVel += gravity * timeStep;
  }

  if (xPos + dx + radius >= canvas.width)
  {
    //hit a wall; there is a bounce

    //find the rest of the interval
    var remainingX = canvas.width-(xPos+radius);

    //find the rest of the time step    
    var remainingTime = remainingX / xVel;

    //no horizontal acceleration

    //friction affects yVel
    yVel *= fWall;

    //elasticity affects xVel
    xVel *= eWall;

    //now you are bouncing back
    //what is time up
    remainingTime = timeStep - remainingTime;

    //set final position
    xPos = canvas.width + (xVel*remainingTime) - radius;

    //no horizontal acceleration
  }
  else if (xPos + dx - radius <= 0) {
    //hit a wall; there is a bounce

    //find the rest of the interval
    var remainingX = (xPos - radius);

    //find the rest of the time step    
    var remainingTime = remainingX / xVel;

    //no horizontal acceleration

    //friction affects yVel
    yVel *= fWall;

    //elasticity affects xVel
    xVel *= eWall;

    //now you are bouncing back
    //what is time up
    remainingTime = timeStep - remainingTime;

    //set final position
    xPos = xVel*remainingTime+radius;

    //no horizontal acceleration
  }
  else {
    //never hit a wall; flying the whole time
    xPos += dx;   
  }
}

function onload()
{
canvas = document.getElementById('canvas');
ctx = canvas.getContext('2d');
canvas.width = window.innerWidth;
canvas.height = window.innerHeight;
radius = 15;
xPos = Math.random()*(canvas.width-(2*radius))+radius;
yPos = Math.random()*(canvas.height-(2*radius))+radius;
xVel = Math.random()*100-50;
yVel = Math.random()*100-50;
gravity = 9.8;
eWall = -1;
eFloor = -.8;
fFloor = .9;
fWall = .9;
interval = 10;
timeStep = .1;//apparent time step

setInterval(update, interval);
}
    </script>
    <style>
    </style>
  </head>
  <body onload="onload()">
    <canvas id="canvas"></canvas>
  </body>
</html>

正文,html{
保证金:0;
填充:0;
}
#帆布{
背景色:黑色;
}
函数drawArc(){
ctx.beginPath();
ctx.fillStyle=“白色”;
弧(xPos,yPos,半径,0,2*Math.PI);
ctx.fill();
ctx.closePath();
};
函数更新(){
clearRect(0,0,canvas.width,canvas.height);
drawArc();
var dx=xVel*时间步长;
var dy=yVel*时间步长;
if(yVel半径和画布高度-(yPos+半径)<.1)
{
yVel=0;
yPos=画布高度-半径;
dy=0;
//摩擦影响xVel
xVel*=fFloor;
}
否则如果(yPos+dy+radius>=画布高度){
//你将在地板下,有一个弹跳
//找出下降间隔的其余部分
var remainingY=画布高度-(yPos+半径);
//找到剩余的时间步长
var剩余时间=剩余时间/yVel;
//加上当时的加速度
yVel+=重力*剩余时间
//摩擦影响xVel
xVel*=fFloor;
//弹性影响yVel
yVel*=eFloor;
//现在你正在反弹
//什么时间到了
剩余时间=时间步长-剩余时间;
//设定最终位置
yPos=画布高度+(yVel*remainingTime)-半径;
//加上当时的加速度
yVel+=重力*剩余时间;
}
其他的
{
//不要撞到地板上,不要一直摔倒
yPos+=dy;
yVel+=重力*时间步长;
}
如果(xPos+dx+radius>=画布宽度)
{
//撞到墙上;有反弹
//找出间隔的其余部分
var remainingX=canvas.width-(xPos+半径);
//找到剩余的时间步长
var剩余时间=剩余时间x/xVel;
//无水平加速度
//摩擦影响yVel
yVel*=fWall;
//弹性影响xVel
xVel*=eWall;
//现在你正在反弹
//什么时间到了
剩余时间=时间步长-剩余时间;
//设定最终位置
xPos=canvas.width+(xVel*remainingTime)-半径;
//无水平加速度
}

否则,如果(xPos+dx-radius)你想让它永远弹跳吗?你期望发生什么?你已经在每一次落地击球中编码,球的速度会降低(摩擦)。因此,球在一段时间后停止移动是正常的。如果你不想失去高度,你需要跟踪每次弹跳时的所有动能。这个答案演示了如何做一个简单的弹跳球,而不是随着时间的推移而失去能量。我不想永远从一个球弹跳到另一个球,我只想自然地停止弹跳,而不是冻结在某一时刻。通过每次将avy减少0.8,您试图模拟一个能量松弛,其中松弛的能量在实际中不是线性的。但是,您可以将其更改为0.9或更大,以获得更长的动画。我不想要无限的反弹,我只想
<html>
  <head>
    <style>
body, html {
  margin: 0;
  padding: 0;
}
#canvas {
  background-color: black;
}
    </style>
    <script>
function drawArc() {
  ctx.beginPath();
  ctx.fillStyle = "white";
  ctx.arc(xPos, yPos, radius, 0, 2 * Math.PI);
  ctx.fill();
  ctx.closePath();
};

function update() {
  ctx.clearRect(0, 0, canvas.width, canvas.height);
  drawArc();
  var dx = xVel*timeStep;
  var dy = yVel*timeStep;

  if(yVel<radius && yVel>-radius && canvas.height-(yPos+radius) < .1)
  {
    yVel = 0;
    yPos = canvas.height-radius;
    dy=0;

    //friction affects xVel
    xVel *= fFloor;
  }
  else if (yPos + dy + radius >= canvas.height) {
    //you will be below the floor; there is a bounce

    //find the rest of the falling interval
    var remainingY = canvas.height-(yPos+radius);

    //find the rest of the time step    
    var remainingTime = remainingY / yVel;

    //add acceleration for that time
    yVel += gravity * remainingTime

    //friction affects xVel
    xVel *= fFloor;

    //elasticity affects yVel
    yVel *= eFloor;

    //now you are bouncing up
    //what is time up
    remainingTime = timeStep - remainingTime;

    //set final position
    yPos = canvas.height + (yVel*remainingTime) - radius;

    //add acceleration for that time
    yVel += gravity * remainingTime;
  }

  else
  {
    //do not hit the floor, falling the whole time
    yPos += dy;
    yVel += gravity * timeStep;
  }

  if (xPos + dx + radius >= canvas.width)
  {
    //hit a wall; there is a bounce

    //find the rest of the interval
    var remainingX = canvas.width-(xPos+radius);

    //find the rest of the time step    
    var remainingTime = remainingX / xVel;

    //no horizontal acceleration

    //friction affects yVel
    yVel *= fWall;

    //elasticity affects xVel
    xVel *= eWall;

    //now you are bouncing back
    //what is time up
    remainingTime = timeStep - remainingTime;

    //set final position
    xPos = canvas.width + (xVel*remainingTime) - radius;

    //no horizontal acceleration
  }
  else if (xPos + dx - radius <= 0) {
    //hit a wall; there is a bounce

    //find the rest of the interval
    var remainingX = (xPos - radius);

    //find the rest of the time step    
    var remainingTime = remainingX / xVel;

    //no horizontal acceleration

    //friction affects yVel
    yVel *= fWall;

    //elasticity affects xVel
    xVel *= eWall;

    //now you are bouncing back
    //what is time up
    remainingTime = timeStep - remainingTime;

    //set final position
    xPos = xVel*remainingTime+radius;

    //no horizontal acceleration
  }
  else {
    //never hit a wall; flying the whole time
    xPos += dx;   
  }
}

function onload()
{
canvas = document.getElementById('canvas');
ctx = canvas.getContext('2d');
canvas.width = window.innerWidth;
canvas.height = window.innerHeight;
radius = 15;
xPos = Math.random()*(canvas.width-(2*radius))+radius;
yPos = Math.random()*(canvas.height-(2*radius))+radius;
xVel = Math.random()*100-50;
yVel = Math.random()*100-50;
gravity = 9.8;
eWall = -1;
eFloor = -.8;
fFloor = .9;
fWall = .9;
interval = 10;
timeStep = .1;//apparent time step

setInterval(update, interval);
}
    </script>
    <style>
    </style>
  </head>
  <body onload="onload()">
    <canvas id="canvas"></canvas>
  </body>
</html>