Физический движок
Пытаюсь написать простейший физический движок(падение точки под углом с нач скоростью)
вот здесь есть демо того что уже получилось(отрисовка на canvas, проверял только в chromium 9.0.564.0): http://i-alexandr-sh.narod.ru/dv.html как видно из демо проблема в том что бы отловить момент когда точка начинает "кататься" по низу полотна, мб кто-нить подскажет как это сделать? Вот код: var point = function(context,color,x,y,a,v,mx,my){ this.context = context; this.x = x; this.y = y; this.a = a; this.v = v; this.mx = mx; this.my = my; this.vx = this.v*Math.cos(this.a/180*Math.PI); this.vy = this.v*Math.sin(this.a/180*Math.PI); this.color = color return true; }; point.prototype.step = function(){ if(this.x+this.vx>this.mx){this.vx*=-1;this.x=this.mx;} else if(this.x+this.vx<0){this.vx*=-1;this.x=0;} else{this.x += this.vx;}; if(this.y+this.vy>this.my){this.vy*=-1;this.y=this.my;} else if(this.y+this.vy<0){this.vy*=-1;this.y=0;} else {this.y += this.vy;}; if(this.y+this.vy>0){this.vy += 9.8;}; return true; }; point.prototype.show = function(){ this.context.fillStyle = this.color; this.context.fillRect(this.x,this.y,10,10); return true; }; point.prototype.hide = function(){ this.context.fillStyle = "#ffffff"; this.context.fillRect(this.x,this.y,10,10); return true; }; point.prototype.loop = function(){ this.hide(); this.step(); this.show(); return true; } window.onload = function(){ canvas = document.getElementById("surf"); context = canvas.getContext("2d"); //context.fillRect(100,100,100,100); var top = new point(context,"#000000",0,0,20,10,300,280) var ID = setInterval(function(){ top.loop(); if (document.getElementById("pause").value!=0) clearInterval(ID); },100); return true; }; |
А в чём проблема смотреть на изменение вертикальной составляющей. Не меняется, значит, катаемся.
|
Проблема в том что оно никогда не равно нулю.
point.prototype.step = function(){ if(this.x+this.vx>this.mx){this.vx*=-1;this.x=this.mx;} else if(this.x+this.vx<0){this.vx*=-1;this.x=0;} else{this.x += this.vx;}; if(this.y+this.vy>this.my){this.vy*=-1;this.y=this.my;} else if(this.y+this.vy<0){this.vy*=-1;this.y=0;} else {this.y += this.vy;}; if(this.vy==0){this.vx=0;this.vy=0;document.getElementById("pause").value=1;}; if(this.y+this.vy>0){this.vy += 9.8;}; return true; }; не помогает. и даже если сделать примерно так: if(this.vy<3 && this.y>-3){this.vx=0;this.vy=0;document.getElementById("pause").value=1;}; Тоже не помогает, если ещё на единицу увеличить мин. скорость то анимация даже не запускается |
Надо к целым числам округлять, на экране всё равно дробных нет.
|
У тебя должно совпасть два условия f(y)=0 и a=0, при этом "а" зависит от "g" и -> 0.
Вроде все правильно сказал. Вот, почитай для начала ускорение и ускорение свободного падения |
ascrazy,
Реализация подсказки Цитата:
<!DOCTYPE html> <html> <meta http-equiv='content-type' content='text/html; charset=windows-1251' /> <script type='text/javascript' > var point = function(context,color,x,y,a,v,mx,my){ this.context = context; this.x = x; this.y = y; this.a = a; this.v = v; this.mx = mx; this.my = my; this.vx = this.v*Math.cos(this.a/180*Math.PI); this.vy = this.v*Math.sin(this.a/180*Math.PI); this.color = color return true; }; point.prototype.step = function(){ if(this.x+this.vx>this.mx){this.vx*=-1;this.x=this.mx;} else if(this.x+this.vx<0){this.vx*=-1;this.x=0;} else{this.x += this.vx;}; if(this.y+this.vy>this.my){this.vy*=-1;this.y=this.my;} else if(this.y+this.vy<0){this.vy*=-1;this.y=0;} else {this.y += this.vy;}; if(this.y+this.vy>0){this.vy += 9.8;}; if(this.stop==this.y){this.vx=0;this.vy=0;document.getElementById("pause").value=1;}; this.stop=this.y; return true; }; point.prototype.show = function(){ this.context.fillStyle = this.color; this.context.fillRect(this.x,this.y,10,10); return true; }; point.prototype.hide = function(){ this.context.fillStyle = "#ffffff"; this.context.fillRect(this.x,this.y,10,10); return true; }; point.prototype.loop = function(){ this.hide(); this.step(); this.show(); return true; } window.onload = function(){ canvas = document.getElementById("surf"); context = canvas.getContext("2d"); //context.fillRect(100,100,100,100); var top = new point(context,"#000000",0,0,20,10,300,280) var ID = setInterval(function(){ top.loop(); if (document.getElementById("pause").value!=0) clearInterval(ID); },100); return true; }; </script> <body> <canvas id='surf' width='300px' height='300px'></canvas> <input id='pause' type='hidden' value='0' /> <input type='button' value='stop' onClick='document.getElementById("pause").value = 1' /> </body> </html> |
Если все сводится к пикселам - действительно округлять. Если некий физический смысл нужен - вводится размер некой погрешности которым можно пренебречь.
Если вертикальная составляющая менее погрешности - нет прижка. |
Часовой пояс GMT +3, время: 09:06. |