JavaScript-mechanics
Если у вас отображается старая версия программы - нажмите "Ctrl + F5"
Левая клавиша мыши по шарику - перетаскивание.
Левая клавиша мыши по полю - заморозить шарик.
Текст программы на языке JavaScript (разработчики Кривцов Антон, Цветков Денис, использована библиотека oCanvas): <toggledisplay status=hide showtext="Показать↓" hidetext="Скрыть↑" linkstyle="font-size:default"> Файл "mechanics.js" <syntaxhighlight lang="javascript" line start="1" enclose="div"> function MainMech(canvas) {
// Предварительные установки
var context = canvas.getContext("2d");
const Pi = 3.1415926; // число "пи"
const m0 = 1; // масштаб массы const T0 = 1; // масштаб времени (период колебаний исходной системы) const a0 = 1; // масштаб расстояния (диаметр шара)
const g0 = 2 * a0 / T0 / T0; // масштаб ускорения (ускорение, при котором за T0 будет пройдено расстояние a0)
const k0 = 2 * Pi / T0; // масштаб частоты const C0 = m0 * k0 * k0; // масштаб жесткости const B0 = 2 * m0 * k0; // масштаб вязкости
// *** Задание физических параметров ***
const Ny = 5; // Число шаров, помещающихся по вертикали в окно (задает размер шара относительно размера окна) const m = 1 * m0; // масса const C = 4 * C0; // жесткость const B = 0.003 * B0; // вязкость среды const B1 = 0.03 * B0; // вязкость на стенках const mg = 1 * m * g0; // сила тяжести // *** Задание вычислительных параметров ***
const fps = 4 * 29; // frames per second - число кадров в секунду (качечтво отображения) const spf = 1000; // steps per frame - число шагов интегрирования между кадрами (edtkbxbdftn скорость расчета) const dt = 0.01 * T0 / fps; // шаг интегрирования (качество расчета)
// Выполнение программы
var scale = canvas.height / Ny / a0;// масштабный коэффициент для перехода от расчетных к экранным координатам var w = canvas.width / scale; // ширина окна в расчетных координатах var h = canvas.height / scale; // высота окна в расчетных координатах var r = a0 / 2; // радиус шара
var x = 4 * r; var y = h - r; // начальное положение шара
var count = true; // проводить ли расчет системы
// создаем объект, связанный с элементом canvas на html странице var ocanvas = oCanvas.create({ canvas: "#canvasMech", // canvasMech - id объекта canvas на html странице fps: fps // сколько кадров в секунду });
// создаем шар var arc = ocanvas.display.arc({ x: x * scale, y: y * scale, radius: r * scale, end: 360, // круг 360 градусов fill: "rgba(0, 0, 255, 1)" // цвет }).add();
// захват шара мышью var mx, my; // актуальная позиция мыши arc.dragAndDrop({ changeZindex: true, // если много шариков - захваченный будет нарисован спереди start: function () { count = false; // на время захвата - отключить расчет this.fill = "rgba(0, 0, 255, 0.5)"; // пока держим шарик - он полупрозрачен mx = ocanvas.mouse.x; my = ocanvas.mouse.y; }, move: function () {
x = arc.x / scale; y = arc.y / scale;
vx = .001*(ocanvas.mouse.x-mx)/dt/fps; vy = .001*(ocanvas.mouse.y-my)/dt/fps; mx = ocanvas.mouse.x; my = ocanvas.mouse.y; }, end: function () { count = true; this.fill = "rgba(0, 0, 255, 1)"; // отпускаем шарик - полупрозрачность убирается } }); ocanvas.bind("mousedown", function () {count = false;}); // заморозить фигуру при клике на поле
var fx = 0; var fy = mg; // сила, действующая на шар var vx = 0; var vy = 0; // скорость
function physics(){ // то, что происходит каждый шаг времени
if (!count) return; for (var s=1; s<=spf; s++) {
fx = - B * vx; fy = mg - B * vy; if (y + r > h) { fy += -C * (y + r - h) - B1 * vy; } if (y - r < 0) { fy += -C * (y - r) - B1 * vy;} if (x + r > w) { fx += -C * (x + r - w) - B1 * vx; } if (x - r < 0) { fx += -C * (x - r) - B1 * vx; }
vx += fx / m * dt; vy += fy / m * dt; x += vx * dt; y += vy * dt;
arc.x = x * scale; arc.y = y * scale; }
} ocanvas.setLoop(physics).start(); // функция, выполняющаяся на каждом шаге
} </syntaxhighligh> </toggledisplay>