КП: Штрафной удар по воротам — различия между версиями

Материал из Department of Theoretical and Applied Mechanics
Перейти к: навигация, поиск
(Обсуждение результатов и выводы)
 
(не показано 75 промежуточных версий 11 участников)
Строка 13: Строка 13:
 
== Аннотация проекта ==
 
== Аннотация проекта ==
  
 +
Данный проект посвящен изучению динамики движения футбольного мяча во время штрафного удара. В ходе работы над проектом был рассмотрен конкретный штрафной удар, который был исполнен Роберто Карлосом в товарищеском матче Бразилия - Франция. Этот удар был симулирован на языке JavaScript <ref>[https://ru.wikipedia.org/wiki/JavaScript JavaScript]</ref>.
  
 
== Формулировка задачи ==
 
== Формулировка задачи ==
Смоделировать процесс движения футбольного мяча во время штрфного удара.
+
 
 +
* Написать программу, которая моделирует процесс движения футбольного мяча во время штрафного удара, с учетом внешних сил и воздействий.
  
 
== Общие сведения по теме ==
 
== Общие сведения по теме ==
 
Роберто Карлос забил в 1997 году в ворота сборной Франции невероятный по красоте гол.  
 
Роберто Карлос забил в 1997 году в ворота сборной Франции невероятный по красоте гол.  
  
Мяч был установлен примерно в 30 м от ворот соперников, ближе к правому краю поля. После удара Карлоса мяч полетел далеко в правую сторону, облетел «стенку» в метре от нее и после этого чудесным образом мяч повернул влево и влетел в ворота - к изумлению игроков, вратаря и представителей СМИ.
+
Мяч был установлен примерно в 30 - 35 м от ворот соперников, ближе к правому краю поля. После удара Карлоса мяч полетел далеко в правую сторону, облетел «стенку» в метре от нее и после этого чудесным образом мяч повернул влево и влетел в ворота - к изумлению игроков, вратаря и представителей СМИ.
  
 
Этот удар стал наглядным примером силы Магнуса, действующей на тело, движущееся с вращением при обтекании его потоком жидкости или газа.
 
Этот удар стал наглядным примером силы Магнуса, действующей на тело, движущееся с вращением при обтекании его потоком жидкости или газа.
 +
 
[[Файл:g33viT3.gif|thumb|Траектория движения мяча во время штрафного удара|450px]]
 
[[Файл:g33viT3.gif|thumb|Траектория движения мяча во время штрафного удара|450px]]
  
 
== Решение ==
 
== Решение ==
[[Файл:Kursovaia.jpg|thumb|Положение мяча и стенки из игроков во время исполнения штрафного удара|450px]]
+
<math>\vec{F_{р}} = \vec{F_{тяж}} + \vec{F_{сопр}} + \vec{F_{м}}  </math>, где
 +
 
 +
<math> \vec{F_{р}} </math> - Равнодействующая сил на мяч;
 +
 
 +
<math> \vec{F_{тяж}} </math> - Сила тяжести, действующая на мяч;
 +
 
 +
<math> \vec{F_{сопр}} </math> - Сила сопротивления воздуха;
 +
 
 +
<math> \vec{F_{м}} </math> - Сила Магнуса <ref>
 +
[https://ru.wikipedia.org/wiki/Эффект_Магнуса Эффект Магнуса]</ref>.
 +
 
 +
 
 +
Сила тяжести:
 +
 
 +
<big><math> \vec{F_{тяж}} = m\vec{g} </math></big>, где
 +
 +
<math> m </math> - масса мяча;
 +
 
 +
<math> g </math> - ускорение свободного падения.
 +
 
 +
 
 +
Силу сопротивления воздуха будем считать с помощью закона Стокса:
 +
 
 +
<big><math>\vec{F} = -6πrη\vec{v} </math></big> , где
 +
 
 +
<math>\vec{F}</math> - сила Стокса,
 +
 
 +
<math>r</math> - радиус мяча,
 +
 
 +
<math>η</math> - динамическая вязкость,
 +
 
 +
<math>\vec{v}</math> - скорость мяча.
 +
 
 +
 
 +
Силу Магнуса примем вида:
 +
 
 +
<big><math>\vec{F} = 2Sρr\vec{u}\times\vec{ω} </math></big>  , где
 +
 
 +
<math>\vec{F}</math> - сила Магнуса,
 +
 
 +
<math>S</math> - площадь, на которую действует сила
 +
 
 +
<math>ρ</math> - плотность воздуха,
 +
 
 +
<math>r</math> - радиус мяча,
 +
 
 +
<math>\vec{u}</math> - относительная скорость мяча,
 +
 
 +
<math>\vec{ω}</math> - угловая скорость мяча.
 +
 
 +
Применив метод Эйлера, получим формулы для нахождения скорости и координаты мяча:
 +
 
 +
<big><math>
 +
\begin{cases}
 +
v_x^{i+1} = v_x^i + (-6πrηv_x^i/m + 2πρr^3(u_z^iω_y - u_y^iω_z)/m)\Delta t  \\
 +
v_y^{i+1} = v_y^i + (-6πrηv_y^i/m + 2πρr^3(u_x^iω_z - u_z^iω_x)/m)\Delta t  \\
 +
v_z^{i+1} = v_z^i + (-g-6πrηv_z^i/m + 2πρr^3(u_y^iω_x - u_x^iω_y)/m)\Delta t  \\
 +
\end{cases}
 +
</math></big>
 +
 
 +
<big><math>
 +
\begin{cases}
 +
x^{i+1} = x^i + v_x^i\Delta t \\
 +
y^{i+1} = y^i + v_y^i\Delta t \\
 +
z^{i+1} = z^i + v_z^i\Delta t \\
 +
\end{cases}
 +
</math></big>;
 +
 
 +
 
 +
'''Возможности программы:'''
 +
 
 +
 
 +
* По нажатию кнопки "Start" запускается процесс прорисовки траектории полета мяча, с выставленными параметрами.
 +
* По нажатию кнопки "Update" мы обновляем страницу и можем выставить новые начальные значения(условия) полета мяча.
 +
{{#widget:Iframe |url=http://tm.spbstu.ru/htmlets/filimonov/K_NIR.html |width=1150 |height=575 |border=0 }}
 +
 
 +
<div class="mw-collapsible mw-collapsed">
 +
'''Текст программы на языке JavaScript:''' <div class="mw-collapsible-content">
 +
<syntaxhighlight lang="javascript" line start="1" enclose="div">
 +
 
 +
function main()
 +
{
 +
  var scene = new THREE.Scene();
 +
  var camera = new THREE.PerspectiveCamera(45, window.innerWidth/window.innerHeight, 0.1, 1000);
 +
  var render = new THREE.WebGLRenderer();
 +
  render.setClearColor(0x87CEFA, 1);
 +
  render.setSize(900, 450);
 +
 
 +
  //Половина футбольного поля
 +
   
 +
  var planeGeometry = new THREE.PlaneGeometry(52.5,70,32,32);
 +
  var planeMaterial = new THREE.MeshLambertMaterial({color:0x009900});
 +
  var plane = new THREE.Mesh(planeGeometry, planeMaterial);
 +
  plane.position.x=0;
 +
  plane.position.y=0;
 +
  plane.position.z=0;
 +
  scene.add(plane);
 +
  //
 +
  // Центр поля
 +
 
 +
  var line_geometry = new THREE.Geometry();
 +
    line_geometry.vertices.push(new THREE.Vector3(-26.25,-35,0));
 +
    line_geometry.vertices.push(new THREE.Vector3(-26.25,35,0));
 +
  var  material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
 +
  var line1 = new THREE.Line(line_geometry,material_line); 
 +
 
 +
        scene.add( line1 );
 +
 
 +
  var curve = new THREE.EllipseCurve(
 +
  -26.25,  0,            // ax, aY
 +
  9.15, 9.15,          // xRadius, yRadius
 +
  -0.5*Math.PI,  -1.5*Math.PI,  // aStartAngle, aEndAngle
 +
  false            // aClockwise
 +
  );
 +
 
 +
  var path = new THREE.Path( curve.getPoints( 50 ) );
 +
  var geometry = path.createPointsGeometry( 50 );
 +
  var material = new THREE.LineBasicMaterial( { color : 0xffffff } );
 +
 
 +
// Create the final Object3d to add to the scene
 +
  var ellipse = new THREE.Line( geometry, material );
 +
  scene.add(ellipse);
 +
  ellipse.position.x=0;
 +
  ellipse.position.y=0;
 +
  ellipse.position.z=0;
 +
  //
 +
  //Штрафная
 +
  var line_geometry = new THREE.Geometry();
 +
    line_geometry.vertices.push(new THREE.Vector3(26.25,20.16,0));
 +
    line_geometry.vertices.push(new THREE.Vector3(9.75,20.16,0));
 +
  var  material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
 +
  var line = new THREE.Line(line_geometry,material_line); 
 +
 
 +
        scene.add( line );
 +
  var line_geometry = new THREE.Geometry();
 +
    line_geometry.vertices.push(new THREE.Vector3(26.25,-20.16,0));
 +
    line_geometry.vertices.push(new THREE.Vector3(9.75,-20.16,0));
 +
  var  material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
 +
  var line2 = new THREE.Line(line_geometry,material_line); 
 +
 
 +
        scene.add( line2 );
 +
 
 +
  var line_geometry = new THREE.Geometry();
 +
    line_geometry.vertices.push(new THREE.Vector3(9.75,-20.16,0));
 +
    line_geometry.vertices.push(new THREE.Vector3(9.75,20.16,0));
 +
  var  material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
 +
  var line3 = new THREE.Line(line_geometry,material_line); 
 +
 
 +
        scene.add( line3 );
 +
  // вратарская зона
 +
  var line_geometry = new THREE.Geometry();
 +
    line_geometry.vertices.push(new THREE.Vector3(20.75,-9.16,0));
 +
    line_geometry.vertices.push(new THREE.Vector3(26.25,-9.16,0));
 +
  var  material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
 +
  var line4 = new THREE.Line(line_geometry,material_line); 
 +
 
 +
        scene.add( line4 );
 +
 
 +
  var line_geometry = new THREE.Geometry();
 +
    line_geometry.vertices.push(new THREE.Vector3(20.75,9.16,0));
 +
    line_geometry.vertices.push(new THREE.Vector3(26.25,9.16,0));
 +
  var  material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
 +
  var line5 = new THREE.Line(line_geometry,material_line); 
 +
 
 +
        scene.add( line5 );
 +
 
 +
  var line_geometry = new THREE.Geometry();
 +
    line_geometry.vertices.push(new THREE.Vector3(20.75,-9.16,0));
 +
    line_geometry.vertices.push(new THREE.Vector3(20.75,9.16,0));
 +
  var  material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
 +
  var line6 = new THREE.Line(line_geometry,material_line); 
 +
 
 +
        scene.add( line6 );
 +
  //
 +
  // ворота
 +
  var line_geometry = new THREE.Geometry();
 +
    line_geometry.vertices.push(new THREE.Vector3(26.25,-3.66,0));
 +
    line_geometry.vertices.push(new THREE.Vector3(26.25,3.66,0));
 +
  var  material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
 +
  var line7 = new THREE.Line(line_geometry,material_line); 
 +
 
 +
        scene.add( line7 );
 +
   
 +
  var line_geometry = new THREE.Geometry();
 +
    line_geometry.vertices.push(new THREE.Vector3(26.23,-3.66,0));
 +
    line_geometry.vertices.push(new THREE.Vector3(26.23,3.66,0));
 +
  var  material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
 +
  var line8 = new THREE.Line(line_geometry,material_line); 
 +
 
 +
        scene.add( line8 );
 +
 
 +
  var line_geometry = new THREE.Geometry();
 +
    line_geometry.vertices.push(new THREE.Vector3(26.22,-3.66,0));
 +
    line_geometry.vertices.push(new THREE.Vector3(26.22,3.66,0));
 +
  var  material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
 +
  var line9 = new THREE.Line(line_geometry,material_line); 
 +
 
 +
        scene.add( line9 );
 +
   
 +
  var geometry = new THREE.CylinderGeometry( 0.12, 0.12, 2.44, 32 );
 +
  var material = new THREE.MeshBasicMaterial( {color: 0x000000} );
 +
  var cylinder = new THREE.Mesh( geometry, material );
 +
  cylinder.rotation.x=0.5*Math.PI;
 +
  cylinder.position.x=26.25;
 +
  cylinder.position.y=-3.66;
 +
  cylinder.position.z=1.22;
 +
  scene.add( cylinder );
 +
 
 +
  var geometry = new THREE.CylinderGeometry( 0.12, 0.12, 2.44, 32 );
 +
  var material = new THREE.MeshBasicMaterial( {color: 0x000000} );
 +
  var cylinder1 = new THREE.Mesh( geometry, material );
 +
  cylinder1.rotation.x=0.5*Math.PI;
 +
  cylinder1.position.x=26.25;
 +
  cylinder1.position.y=3.66;
 +
  cylinder1.position.z=1.22;
 +
  scene.add( cylinder1 );
 +
 
 +
  var geometry = new THREE.CylinderGeometry( 0.12, 0.12, 7.56, 32 );
 +
  var material = new THREE.MeshBasicMaterial( {color: 0x000000} );
 +
  var cylinder1 = new THREE.Mesh( geometry, material );
 +
  cylinder1.position.x=26.25;
 +
  cylinder1.position.y=0;
 +
  cylinder1.position.z=2.44;
 +
  scene.add( cylinder1 );
 +
  //
 +
  var curve = new THREE.EllipseCurve(
 +
  15.25,  0,            // ax, aY
 +
  9.15, 9.15,          // xRadius, yRadius
 +
  0.7*Math.PI,  -0.7*Math.PI,  // aStartAngle, aEndAngle
 +
  false            // aClockwise
 +
  );
 +
 
 +
  var path = new THREE.Path( curve.getPoints( 50 ) );
 +
  var geometry = path.createPointsGeometry( 50 );
 +
  var material = new THREE.LineBasicMaterial( { color : 0xffffff } );
 +
 
 +
// Create the final Object3d to add to the scene
 +
  var ellipse1 = new THREE.Line( geometry, material );
 +
  scene.add(ellipse1);
 +
  ellipse1.position.x=0;
 +
  ellipse1.position.y=0;
 +
  ellipse1.position.z=0;
 +
  //точка пенальти
 +
  var material = new THREE.MeshBasicMaterial({
 +
  color: 0xffffff});
 +
 
 +
  var radius = 0.4;
 +
  var segments = 32;
 +
 
 +
  var circleGeometry = new THREE.CircleGeometry( radius, segments );       
 +
  var circle = new THREE.Mesh( circleGeometry, material );
 +
  scene.add( circle );
 +
  circle.position.x=15.25;
 +
  circle.position.y=0;
 +
  circle.position.z=0;
 +
  // мяч
 +
 
 +
 
 +
  var geometry = new THREE.SphereGeometry( 0.25, 32, 32 );
 +
  var material = new THREE.MeshBasicMaterial( {color: 0xff0000} );
 +
  var sphere = new THREE.Mesh( geometry, material );
 +
  scene.add( sphere );
 +
  sphere.position.x=-8.75;
 +
  sphere.position.y=-0.75;
 +
  sphere.position.z=0.25;
 +
  //
 +
  //стенка
 +
  /**var planeGeometry = new THREE.PlaneGeometry(1,4,1,1);
 +
    var planeMaterial = new THREE.MeshBasicMaterial({color: 0xcccccc});
 +
    var plane = new THREE.Mesh(planeGeometry,planeMaterial);
 +
    plane.position.x = 0,75;
 +
    plane.position.y = -1,66;
 +
    plane.position.z = 0;
 +
    scene.add(plane);*/
 +
 
 +
  var geometry = new THREE.BoxGeometry( 0.5, 3.5, 1.8 );
 +
  var material = new THREE.MeshBasicMaterial( {color: 0xcccccc} );
 +
  var cube = new THREE.Mesh( geometry, material );
 +
  cube.position.x = 0.75;
 +
    cube.position.y = 0;
 +
    cube.position.z = 0.9;
 +
  scene.add( cube );
 +
 
 +
    var radius1 = 0.25;
 +
  var segments1 = 32;
 +
 
 +
  var circle1Geometry = new THREE.CircleGeometry( radius1, segments1 );       
 +
  var circle1 = new THREE.Mesh( circle1Geometry, material );
 +
  scene.add( circle1 );
 +
  circle1.position.x=0.75;
 +
  circle1.position.y=-0.5;
 +
  circle1.position.z=0.9;
 +
 
 +
 
 +
 
 +
  // положение камеры
 +
  camera.position.x= 0;
 +
  camera.position.y= 0;
 +
  camera.position.z= 80;
 +
  camera.lookAt(scene.position);
 +
  $("#webGL").append(render.domElement);
 +
 
 +
  var  spotLight = new THREE.SpotLight(0xffffff);
 +
  spotLight.position.set(0,0,250) 
 +
  scene.add(spotLight);
 +
 
 +
  var trajectoryGeometry = new THREE.SphereGeometry(0.1, 16, 16);
 +
  var trajectoryMaterial = new THREE.MeshBasicMaterial( {color: 0x000000,wireframe:true} );
 +
 
 +
 
 +
 
 +
  var controls = new function() {
 +
    this.viscosity = 0.0000178;
 +
    this.AirDensity = 1.2754;
 +
    this.WindPowerX = 0;
 +
    this.WindPowerY = 0;
 +
    this.WindPowerZ = 0;
 +
    this.BallX_AngularVelocity = 0;
 +
    this.BallY_AngularVelocity =  0;
 +
    this.BallZ_AngularVelocity = 10 * 6.28318530718;
 +
    this.BallVelocityX = 35;
 +
    this.BallVelocityY = -8.5;
 +
    this.BallVelocityZ = 2.8;
 +
  }
 +
  var gui = new dat.GUI();
 +
  gui.add(controls, 'viscosity',1,1.5);
 +
  gui.add(controls, 'AirDensity',1,1.5);
 +
 
 +
 
 +
  var guiScale = gui.addFolder('WindPower');
 +
  guiScale.add(controls, 'WindPowerX', -100,100);
 +
  guiScale.add(controls, 'WindPowerY', -100,100);
 +
  guiScale.add(controls, 'WindPowerZ', -100,100);
 +
 
 +
  var guiPosition = gui.addFolder('AngularVelocity');
 +
  guiPosition.add(controls, 'BallX_AngularVelocity', -100,100);
 +
  guiPosition.add(controls, 'BallY_AngularVelocity', -100,100);
 +
  guiPosition.add(controls, 'BallZ_AngularVelocity', -100,100);
 +
 
 +
  var guiRotation = gui.addFolder('BallLineVelocity');
 +
  guiRotation.add(controls, 'BallVelocityX', 0,50);
 +
  guiRotation.add(controls, 'BallVelocityY', -50,50);
 +
  guiRotation.add(controls, 'BallVelocityZ', 0,50);
 +
 
 +
  control1 = new THREE.OrbitControls(camera);
 +
  control1.dumping = 0.2;
 +
 
 +
 
 +
 
 +
 
 +
 
 +
  window.addEventListener('resize',onWindowResize,false);
 +
  function onWindowResize()
 +
  {
 +
  camera.aspect = window.innerWidth/window.innerHeight;
 +
  camera.updateProjectionMatrix();
 +
  render.setSize(window.innerWidth,window.innerHeight);
 +
 
 +
  renderer();
 +
}
 +
  //var stats = initStats();
 +
  var step = 0;
 +
 
 +
 
 +
 
 +
 
 +
  var pi = Math.PI;
 +
  var r = 0.11;
 +
  var ro = controls.AirDensity;
 +
  var nu = controls.viscosity;
 +
  var m = 0.45;
 +
  var i = 0;
 +
  var vX = 0;
 +
  var vY = 0;
 +
  var vZ = 0;
 +
  var Wx = controls.BallX_AngularVelocity ;
 +
  var Wy = controls.BallY_AngularVelocity ;
 +
  var Wz = controls.BallZ_AngularVelocity ;
 +
  var dt = 0.01;
 +
  var g = 9.81
 +
 
 +
  vX += controls.BallVelocityX;
 +
  vY += controls.BallVelocityY;
 +
  vZ += controls.BallVelocityZ;
 +
 
 +
  function renderer()
 +
  {
 +
    //stats.update();
 +
 
 +
   
 +
        if (i == 0)
 +
    {
 +
      vX += controls.BallVelocityX;
 +
      vY += controls.BallVelocityY;
 +
      vZ += controls.BallVelocityZ;
 +
      windX = controls.WindPowerX;
 +
      windY =  controls.WindPowerY;
 +
      windZ =  controls.WindPowerZ;
 +
     
 +
      Wx = controls.BallX_AngularVelocity;
 +
      Wy = controls.BallY_AngularVelocity;
 +
      Wz = controls.BallZ_AngularVelocity;
 +
           
 +
      i = 1;
 +
     
 +
    }
 +
     
 +
 
 +
      if (sphere.position.z >= 0.25 && sphere.position.x <= 40)
 +
      {
 +
    var Ux = vX-windX;
 +
    var Uy = vY-windY;
 +
    var Uz = vZ-windZ;
 +
      vX += (-6*pi*r*nu*vX/m + 2*pi*ro*r*r*r*((Uz)*Wy-((Uz))*Wz)/m)*dt;
 +
      vY += (-6*pi*r*nu*vY/m + 2*pi*ro*r*r*r*((Ux)*Wz)-((Uz))*Wx/m)*dt;
 +
      vZ += (-g-6*pi*r*nu*vZ/m + 2*pi*ro*r*r*r*((Uy)*Wx-((Ux))*Wy)/m)*dt;
 +
     
 +
 
 +
      sphere.position.x += vX*dt;
 +
      sphere.position.y += vY*dt;
 +
      sphere.position.z += vZ*dt;
 +
         
 +
      var trajectory = new THREE.Mesh(trajectoryGeometry, trajectoryMaterial);
 +
      trajectory.position.x = sphere.position.x;
 +
      trajectory.position.y = sphere.position.y;
 +
      trajectory.position.z = sphere.position.z;
 +
     
 +
      scene.add( trajectory );
 +
      }
 +
     
 +
   
 +
    requestAnimationFrame(renderer);
 +
    control1.update();
 +
    render.render(scene,camera);
 +
   
 +
 
 +
  }
 +
  this.start = renderer;
 +
 
 +
}
 +
 
 +
 
 +
</syntaxhighlight>
 +
</div>
  
 
== Обсуждение результатов и выводы ==
 
== Обсуждение результатов и выводы ==
  
 +
* Таким образом, в ходе работы над проектом была написана программа, моделирующая траекторию движения мяча во время штрафного удара, а так же смоделирован конкретный удар, при известных условиях.
 +
 +
{{начало цитаты}}
 +
 +
'''Входные данные'''
 +
 +
* На основании статьи <ref>[http://technicamolodezhi.ru/rubriki_tm/tehnika_i_sport/fizika_futbola статья "Физика футбола"]</ref>, посвященной удару Роберто Карлоса можно вычленить входные данные для нашей программы и посмотреть на полученную в программе траекторию.
 +
 +
- <big><math> v_{0} = 35 (м/с) </math> - начальная скорость мяча</big>;
 +
 +
- <big><math> d = 35 (м) </math> - расстояние от мяча до ворот</big>;
 +
 +
- <big><math> \omega_{z} = 10 (об/с) =62.8 (рад/с)</math> - скорость вращения мяча во время полета</big>;
 +
 +
- <big>Также было известно, что погода была сухая и  безветренная, то есть скорость ветра по всем осям равна 0.</big>
 +
 +
* ''' Подставив в программу данные, полученные учеными, можно увидеть как мяч залетает в ворота.'''
 +
 +
{{конец цитаты}}
 +
 +
'''Вывод:'''
 +
В случае, когда удар нанесен с другой угловой скоростью ( <math> \omega_{z} = 9 (об/с)</math>, в результате работы программы  можно увидеть, что мяч не залетает в ворота.
 +
 +
При угловой скорости мяча <math> \omega_{z} = 9 (об/с) </math> и при увеличении проекции начальной скорости в направлении удара <math> v_{x} = 45 (м/с) </math>, но с теми же значениями по ортогональным осям, мяч залетает в ворота.
 +
 +
На основании полученных результатов можно сказать, что мяч залетел с немалой долей удачи, так как даже с малым изменением параметров меняется вероятность попадания.
 +
.
  
 
<br>
 
<br>
Скачать отчет:
+
Скачать отчет:[[Медиа:KursovoyProektFilimonov.docx | Отчет]]
 
<br>
 
<br>
 
Скачать презентацию:
 
Скачать презентацию:
Строка 38: Строка 511:
 
== Ссылки по теме ==
 
== Ссылки по теме ==
  
 +
== Примечания ==
 +
<references/>
  
 
== См. также ==
 
== См. также ==

Текущая версия на 04:07, 5 июня 2015

А.М. Кривцов > Теоретическая механика > Курсовые проекты ТМ 2015 > Штрафной удар по воротам


Курсовой проект по Теоретической механике

Исполнитель: Филимонов Александр

Группа: 09 (23604)

Семестр: весна 2015

Штрайной удар Роберто Карлоса

Аннотация проекта[править]

Данный проект посвящен изучению динамики движения футбольного мяча во время штрафного удара. В ходе работы над проектом был рассмотрен конкретный штрафной удар, который был исполнен Роберто Карлосом в товарищеском матче Бразилия - Франция. Этот удар был симулирован на языке JavaScript [1].

Формулировка задачи[править]

  • Написать программу, которая моделирует процесс движения футбольного мяча во время штрафного удара, с учетом внешних сил и воздействий.

Общие сведения по теме[править]

Роберто Карлос забил в 1997 году в ворота сборной Франции невероятный по красоте гол.

Мяч был установлен примерно в 30 - 35 м от ворот соперников, ближе к правому краю поля. После удара Карлоса мяч полетел далеко в правую сторону, облетел «стенку» в метре от нее и после этого чудесным образом мяч повернул влево и влетел в ворота - к изумлению игроков, вратаря и представителей СМИ.

Этот удар стал наглядным примером силы Магнуса, действующей на тело, движущееся с вращением при обтекании его потоком жидкости или газа.

Траектория движения мяча во время штрафного удара

Решение[править]

[math]\vec{F_{р}} = \vec{F_{тяж}} + \vec{F_{сопр}} + \vec{F_{м}} [/math], где

[math] \vec{F_{р}} [/math] - Равнодействующая сил на мяч;

[math] \vec{F_{тяж}} [/math] - Сила тяжести, действующая на мяч;

[math] \vec{F_{сопр}} [/math] - Сила сопротивления воздуха;

[math] \vec{F_{м}} [/math] - Сила Магнуса [2].


Сила тяжести:

[math] \vec{F_{тяж}} = m\vec{g} [/math], где

[math] m [/math] - масса мяча;

[math] g [/math] - ускорение свободного падения.


Силу сопротивления воздуха будем считать с помощью закона Стокса:

[math]\vec{F} = -6πrη\vec{v} [/math] , где

[math]\vec{F}[/math] - сила Стокса,

[math]r[/math] - радиус мяча,

[math]η[/math] - динамическая вязкость,

[math]\vec{v}[/math] - скорость мяча.


Силу Магнуса примем вида:

[math]\vec{F} = 2Sρr\vec{u}\times\vec{ω} [/math] , где

[math]\vec{F}[/math] - сила Магнуса,

[math]S[/math] - площадь, на которую действует сила

[math]ρ[/math] - плотность воздуха,

[math]r[/math] - радиус мяча,

[math]\vec{u}[/math] - относительная скорость мяча,

[math]\vec{ω}[/math] - угловая скорость мяча.

Применив метод Эйлера, получим формулы для нахождения скорости и координаты мяча:

[math] \begin{cases} v_x^{i+1} = v_x^i + (-6πrηv_x^i/m + 2πρr^3(u_z^iω_y - u_y^iω_z)/m)\Delta t \\ v_y^{i+1} = v_y^i + (-6πrηv_y^i/m + 2πρr^3(u_x^iω_z - u_z^iω_x)/m)\Delta t \\ v_z^{i+1} = v_z^i + (-g-6πrηv_z^i/m + 2πρr^3(u_y^iω_x - u_x^iω_y)/m)\Delta t \\ \end{cases} [/math]

[math] \begin{cases} x^{i+1} = x^i + v_x^i\Delta t \\ y^{i+1} = y^i + v_y^i\Delta t \\ z^{i+1} = z^i + v_z^i\Delta t \\ \end{cases} [/math];


Возможности программы:


  • По нажатию кнопки "Start" запускается процесс прорисовки траектории полета мяча, с выставленными параметрами.
  • По нажатию кнопки "Update" мы обновляем страницу и можем выставить новые начальные значения(условия) полета мяча.

Текст программы на языке JavaScript:
  1 function main()
  2 {
  3   var scene = new THREE.Scene();
  4   var camera = new THREE.PerspectiveCamera(45, window.innerWidth/window.innerHeight, 0.1, 1000);
  5   var render = new THREE.WebGLRenderer();
  6   render.setClearColor(0x87CEFA, 1);
  7   render.setSize(900, 450);
  8   
  9   //Половина футбольного поля
 10     
 11   var planeGeometry = new THREE.PlaneGeometry(52.5,70,32,32);
 12   var planeMaterial = new THREE.MeshLambertMaterial({color:0x009900});
 13   var plane = new THREE.Mesh(planeGeometry, planeMaterial);
 14   plane.position.x=0;
 15   plane.position.y=0;
 16   plane.position.z=0;
 17   scene.add(plane);
 18   //
 19   // Центр поля
 20   
 21   var line_geometry = new THREE.Geometry();
 22     line_geometry.vertices.push(new THREE.Vector3(-26.25,-35,0));
 23     line_geometry.vertices.push(new THREE.Vector3(-26.25,35,0));
 24   var   material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
 25   var line1 = new THREE.Line(line_geometry,material_line);  
 26 
 27         scene.add( line1 );
 28 
 29   var curve = new THREE.EllipseCurve(
 30   -26.25,  0,            // ax, aY
 31   9.15, 9.15,           // xRadius, yRadius
 32   -0.5*Math.PI,  -1.5*Math.PI,  // aStartAngle, aEndAngle
 33   false             // aClockwise
 34   );
 35 
 36   var path = new THREE.Path( curve.getPoints( 50 ) );
 37   var geometry = path.createPointsGeometry( 50 );
 38   var material = new THREE.LineBasicMaterial( { color : 0xffffff } );
 39 
 40 // Create the final Object3d to add to the scene
 41   var ellipse = new THREE.Line( geometry, material );
 42   scene.add(ellipse);
 43   ellipse.position.x=0;
 44   ellipse.position.y=0;
 45   ellipse.position.z=0;
 46   //
 47   //Штрафная
 48   var line_geometry = new THREE.Geometry();
 49     line_geometry.vertices.push(new THREE.Vector3(26.25,20.16,0));
 50     line_geometry.vertices.push(new THREE.Vector3(9.75,20.16,0));
 51   var   material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
 52   var line = new THREE.Line(line_geometry,material_line);  
 53 
 54         scene.add( line );
 55   var line_geometry = new THREE.Geometry();
 56     line_geometry.vertices.push(new THREE.Vector3(26.25,-20.16,0));
 57     line_geometry.vertices.push(new THREE.Vector3(9.75,-20.16,0));
 58   var   material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
 59   var line2 = new THREE.Line(line_geometry,material_line);  
 60 
 61         scene.add( line2 );
 62   
 63   var line_geometry = new THREE.Geometry();
 64     line_geometry.vertices.push(new THREE.Vector3(9.75,-20.16,0));
 65     line_geometry.vertices.push(new THREE.Vector3(9.75,20.16,0));
 66   var   material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
 67   var line3 = new THREE.Line(line_geometry,material_line);  
 68 
 69         scene.add( line3 );
 70   // вратарская зона
 71   var line_geometry = new THREE.Geometry();
 72     line_geometry.vertices.push(new THREE.Vector3(20.75,-9.16,0));
 73     line_geometry.vertices.push(new THREE.Vector3(26.25,-9.16,0));
 74   var   material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
 75   var line4 = new THREE.Line(line_geometry,material_line);  
 76 
 77         scene.add( line4 );
 78   
 79   var line_geometry = new THREE.Geometry();
 80     line_geometry.vertices.push(new THREE.Vector3(20.75,9.16,0));
 81     line_geometry.vertices.push(new THREE.Vector3(26.25,9.16,0));
 82   var   material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
 83   var line5 = new THREE.Line(line_geometry,material_line);  
 84 
 85         scene.add( line5 );
 86   
 87   var line_geometry = new THREE.Geometry();
 88     line_geometry.vertices.push(new THREE.Vector3(20.75,-9.16,0));
 89     line_geometry.vertices.push(new THREE.Vector3(20.75,9.16,0));
 90   var   material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
 91   var line6 = new THREE.Line(line_geometry,material_line);  
 92 
 93         scene.add( line6 );
 94   //
 95   // ворота
 96   var line_geometry = new THREE.Geometry();
 97     line_geometry.vertices.push(new THREE.Vector3(26.25,-3.66,0));
 98     line_geometry.vertices.push(new THREE.Vector3(26.25,3.66,0));
 99   var   material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
100   var line7 = new THREE.Line(line_geometry,material_line);  
101 
102         scene.add( line7 );
103     
104   var line_geometry = new THREE.Geometry();
105     line_geometry.vertices.push(new THREE.Vector3(26.23,-3.66,0));
106     line_geometry.vertices.push(new THREE.Vector3(26.23,3.66,0));
107   var   material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
108   var line8 = new THREE.Line(line_geometry,material_line);  
109 
110         scene.add( line8 );
111 
112   var line_geometry = new THREE.Geometry();
113     line_geometry.vertices.push(new THREE.Vector3(26.22,-3.66,0));
114     line_geometry.vertices.push(new THREE.Vector3(26.22,3.66,0));
115   var   material_line = new THREE.LineBasicMaterial({ color: 0xEEEEEE, WireframeLinewidth: 10,wireframe: true, fog:false});
116   var line9 = new THREE.Line(line_geometry,material_line);  
117 
118         scene.add( line9 );
119     
120   var geometry = new THREE.CylinderGeometry( 0.12, 0.12, 2.44, 32 );
121   var material = new THREE.MeshBasicMaterial( {color: 0x000000} );
122   var cylinder = new THREE.Mesh( geometry, material );
123   cylinder.rotation.x=0.5*Math.PI;
124   cylinder.position.x=26.25;
125   cylinder.position.y=-3.66;
126   cylinder.position.z=1.22;
127   scene.add( cylinder );
128   
129   var geometry = new THREE.CylinderGeometry( 0.12, 0.12, 2.44, 32 );
130   var material = new THREE.MeshBasicMaterial( {color: 0x000000} );
131   var cylinder1 = new THREE.Mesh( geometry, material );
132   cylinder1.rotation.x=0.5*Math.PI;
133   cylinder1.position.x=26.25;
134   cylinder1.position.y=3.66;
135   cylinder1.position.z=1.22;
136   scene.add( cylinder1 );
137   
138   var geometry = new THREE.CylinderGeometry( 0.12, 0.12, 7.56, 32 );
139   var material = new THREE.MeshBasicMaterial( {color: 0x000000} );
140   var cylinder1 = new THREE.Mesh( geometry, material );
141   cylinder1.position.x=26.25;
142   cylinder1.position.y=0;
143   cylinder1.position.z=2.44;
144   scene.add( cylinder1 );
145   //
146   var curve = new THREE.EllipseCurve(
147   15.25,  0,            // ax, aY
148   9.15, 9.15,           // xRadius, yRadius
149   0.7*Math.PI,  -0.7*Math.PI,  // aStartAngle, aEndAngle
150   false             // aClockwise
151   );
152 
153   var path = new THREE.Path( curve.getPoints( 50 ) );
154   var geometry = path.createPointsGeometry( 50 );
155   var material = new THREE.LineBasicMaterial( { color : 0xffffff } );
156 
157 // Create the final Object3d to add to the scene
158   var ellipse1 = new THREE.Line( geometry, material );
159   scene.add(ellipse1);
160   ellipse1.position.x=0;
161   ellipse1.position.y=0;
162   ellipse1.position.z=0;
163   //точка пенальти
164   var material = new THREE.MeshBasicMaterial({
165   color: 0xffffff});
166 
167   var radius = 0.4;
168   var segments = 32;
169 
170   var circleGeometry = new THREE.CircleGeometry( radius, segments );        
171   var circle = new THREE.Mesh( circleGeometry, material );
172   scene.add( circle );
173   circle.position.x=15.25;
174   circle.position.y=0;
175   circle.position.z=0;
176   // мяч
177 
178   
179   var geometry = new THREE.SphereGeometry( 0.25, 32, 32 );
180   var material = new THREE.MeshBasicMaterial( {color: 0xff0000} );
181   var sphere = new THREE.Mesh( geometry, material );
182   scene.add( sphere );
183   sphere.position.x=-8.75;
184   sphere.position.y=-0.75;
185   sphere.position.z=0.25;
186   //
187   //стенка
188   /**var planeGeometry = new THREE.PlaneGeometry(1,4,1,1);
189     var planeMaterial = new THREE.MeshBasicMaterial({color: 0xcccccc});
190     var plane = new THREE.Mesh(planeGeometry,planeMaterial);
191     plane.position.x = 0,75;
192     plane.position.y = -1,66;
193     plane.position.z = 0;
194     scene.add(plane);*/
195   
196   var geometry = new THREE.BoxGeometry( 0.5, 3.5, 1.8 );
197   var material = new THREE.MeshBasicMaterial( {color: 0xcccccc} );
198   var cube = new THREE.Mesh( geometry, material );
199   cube.position.x = 0.75;
200     cube.position.y = 0;
201     cube.position.z = 0.9;
202   scene.add( cube );
203   
204     var radius1 = 0.25;
205   var segments1 = 32;
206 
207   var circle1Geometry = new THREE.CircleGeometry( radius1, segments1 );        
208   var circle1 = new THREE.Mesh( circle1Geometry, material );
209   scene.add( circle1 );
210   circle1.position.x=0.75;
211   circle1.position.y=-0.5;
212   circle1.position.z=0.9;
213   
214   
215   
216   // положение камеры
217   camera.position.x= 0;
218   camera.position.y= 0;
219   camera.position.z= 80;
220   camera.lookAt(scene.position);
221   $("#webGL").append(render.domElement);
222   
223   var  spotLight = new THREE.SpotLight(0xffffff);
224   spotLight.position.set(0,0,250)  
225   scene.add(spotLight);
226   
227   var trajectoryGeometry = new THREE.SphereGeometry(0.1, 16, 16);
228   var trajectoryMaterial = new THREE.MeshBasicMaterial( {color: 0x000000,wireframe:true} );
229   
230   
231   
232   var controls = new function() {
233     this.viscosity = 0.0000178;
234     this.AirDensity = 1.2754;
235     this.WindPowerX = 0;
236     this.WindPowerY = 0;
237     this.WindPowerZ = 0;
238     this.BallX_AngularVelocity = 0;
239     this.BallY_AngularVelocity =  0;
240     this.BallZ_AngularVelocity = 10 * 6.28318530718;
241     this.BallVelocityX = 35;
242     this.BallVelocityY = -8.5;
243     this.BallVelocityZ = 2.8;
244   }
245   var gui = new dat.GUI();
246   gui.add(controls, 'viscosity',1,1.5);
247   gui.add(controls, 'AirDensity',1,1.5);
248   
249 
250   var guiScale = gui.addFolder('WindPower');
251   guiScale.add(controls, 'WindPowerX', -100,100);
252   guiScale.add(controls, 'WindPowerY', -100,100);
253   guiScale.add(controls, 'WindPowerZ', -100,100);
254   
255   var guiPosition = gui.addFolder('AngularVelocity');
256   guiPosition.add(controls, 'BallX_AngularVelocity', -100,100);
257   guiPosition.add(controls, 'BallY_AngularVelocity', -100,100);
258   guiPosition.add(controls, 'BallZ_AngularVelocity', -100,100);
259   
260   var guiRotation = gui.addFolder('BallLineVelocity');
261   guiRotation.add(controls, 'BallVelocityX', 0,50);
262   guiRotation.add(controls, 'BallVelocityY', -50,50);
263   guiRotation.add(controls, 'BallVelocityZ', 0,50);
264   
265   control1 = new THREE.OrbitControls(camera);
266   control1.dumping = 0.2;
267 
268 
269 
270 
271   
272   window.addEventListener('resize',onWindowResize,false);
273   function onWindowResize()
274   {
275   camera.aspect = window.innerWidth/window.innerHeight;
276   camera.updateProjectionMatrix();
277   render.setSize(window.innerWidth,window.innerHeight);
278 
279   renderer();
280 }
281   //var stats = initStats();
282   var step = 0;
283   
284   
285   
286   
287   var pi = Math.PI;
288   var r = 0.11;
289   var ro = controls.AirDensity;
290   var nu = controls.viscosity;
291   var m = 0.45;
292   var i = 0;
293   var vX = 0;
294   var vY = 0;
295   var vZ = 0;
296   var Wx = controls.BallX_AngularVelocity ;
297   var Wy = controls.BallY_AngularVelocity ;
298   var Wz = controls.BallZ_AngularVelocity ;
299   var dt = 0.01;
300   var g = 9.81
301   
302   vX += controls.BallVelocityX;
303   vY += controls.BallVelocityY;
304   vZ += controls.BallVelocityZ;
305 
306   function renderer()
307   {
308     //stats.update();
309   
310     
311         if (i == 0) 
312     {
313       vX += controls.BallVelocityX;
314       vY += controls.BallVelocityY;
315       vZ += controls.BallVelocityZ;
316       windX = controls.WindPowerX;
317       windY =  controls.WindPowerY;
318       windZ =  controls.WindPowerZ;
319       
320       Wx = controls.BallX_AngularVelocity;
321       Wy = controls.BallY_AngularVelocity;
322       Wz = controls.BallZ_AngularVelocity;
323             
324       i = 1;
325       
326     }
327       
328   
329       if (sphere.position.z >= 0.25 && sphere.position.x <= 40)
330       {
331     var Ux = vX-windX;
332     var Uy = vY-windY;
333     var Uz = vZ-windZ;
334       vX += (-6*pi*r*nu*vX/m + 2*pi*ro*r*r*r*((Uz)*Wy-((Uz))*Wz)/m)*dt;
335       vY += (-6*pi*r*nu*vY/m + 2*pi*ro*r*r*r*((Ux)*Wz)-((Uz))*Wx/m)*dt;
336       vZ += (-g-6*pi*r*nu*vZ/m + 2*pi*ro*r*r*r*((Uy)*Wx-((Ux))*Wy)/m)*dt;
337       
338 
339       sphere.position.x += vX*dt;
340       sphere.position.y += vY*dt;
341       sphere.position.z += vZ*dt;
342           
343       var trajectory = new THREE.Mesh(trajectoryGeometry, trajectoryMaterial);
344       trajectory.position.x = sphere.position.x;
345       trajectory.position.y = sphere.position.y;
346       trajectory.position.z = sphere.position.z;
347       
348       scene.add( trajectory );
349       }
350       
351     
352     requestAnimationFrame(renderer);
353     control1.update();
354     render.render(scene,camera);
355     
356   
357   }
358   this.start = renderer;
359   
360 }

Обсуждение результатов и выводы[править]

  • Таким образом, в ходе работы над проектом была написана программа, моделирующая траекторию движения мяча во время штрафного удара, а так же смоделирован конкретный удар, при известных условиях.

Входные данные

  • На основании статьи [3], посвященной удару Роберто Карлоса можно вычленить входные данные для нашей программы и посмотреть на полученную в программе траекторию.

- [math] v_{0} = 35 (м/с) [/math] - начальная скорость мяча;

- [math] d = 35 (м) [/math] - расстояние от мяча до ворот;

- [math] \omega_{z} = 10 (об/с) =62.8 (рад/с)[/math] - скорость вращения мяча во время полета;

- Также было известно, что погода была сухая и безветренная, то есть скорость ветра по всем осям равна 0.

  • Подставив в программу данные, полученные учеными, можно увидеть как мяч залетает в ворота.

Вывод: В случае, когда удар нанесен с другой угловой скоростью ( [math] \omega_{z} = 9 (об/с)[/math], в результате работы программы можно увидеть, что мяч не залетает в ворота.

При угловой скорости мяча [math] \omega_{z} = 9 (об/с) [/math] и при увеличении проекции начальной скорости в направлении удара [math] v_{x} = 45 (м/с) [/math], но с теми же значениями по ортогональным осям, мяч залетает в ворота.

На основании полученных результатов можно сказать, что мяч залетел с немалой долей удачи, так как даже с малым изменением параметров меняется вероятность попадания. .


Скачать отчет: Отчет
Скачать презентацию:

Ссылки по теме[править]

Примечания[править]

  1. JavaScript
  2. Эффект Магнуса
  3. статья "Физика футбола"

См. также[править]