-
Notifications
You must be signed in to change notification settings - Fork 0
/
main.js
executable file
·109 lines (99 loc) · 3.34 KB
/
main.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
/**
* Right-hand side of our ODE written as a system of first-order ODEs.
*
* @param objectOfInputs An object containing problem parameters.
* @param t Time (seconds).
* @param vars An array of [x, xDot, theta, thetaDot]
* @return [dx/dt, d2x/dt2, dtheta/dt, d2theta/dt2]
*/
function f(objectOfInputs, t, vars, dt) {
var {g, l0, k, m} = objectOfInputs;
var [x, xDot, theta, thetaDot] = vars;
var xDDot = (l0+x)*thetaDot**2 - k*x/m + g*Math.sin(theta);
var thetaDDot = -g*Math.cos(theta)/(l0+x)-2*xDot*thetaDot/(l0+x);
return [dt*xDot, dt*xDDot, dt*thetaDot, dt*thetaDDot];
}
/**
* Solve the problem using RKF45
*
* @param objectOfInputs An object containing all the problem parameters.
* @return [t, vars]
*/
function RKF45(objectOfInputs) {
// Extract initial from object and add to 2d array
var {x0, xDot0, theta0, thetaDot0} = objectOfInputs;
var vars0 = [[x0, xDot0, theta0, thetaDot0]];
var [t, vars] = RKF45Body(f, objectOfInputs, vars0);
return [t, vars];
}
/**
* Generates a 2D phase plot of x against theta
*
* @param solution An object containing solution data.
* @return Nothing.
*/
function generateXThetaPhasePlot(solution) {
// Extract solution data from solution object
var {vars} = solution;
var x = vars[0];
var theta = vars[2];
// Generate 2D plot
gen2DPlot(x, theta, "phasePlotXTheta", "Phase plot of theta against x");
}
/**
* Generates a xdot against x phase plot
*
* @param solution An object containing solution data.
* @return Nothing.
*/
function generateXXDotPhasePlot(solution) {
// Extract solution data from solution object
var {vars} = solution;
var x = vars[0];
var xDot = vars[1];
// Generate 2D plot
gen2DPlot(x, xDot, "phasePlotXXDot", "Phase plot of x dot against x");
}
/**
* Generates a theta dot against theta phase plot
*
* @param solution An object containing solution data.
* @return Nothing.
*/
function generateThetaThetaDotPhasePlot(solution) {
// Extract solution data from solution object
var {vars} = solution;
var theta = vars[2];
var thetaDot = vars[3];
// Generate 2D plot
gen2DPlot(theta, thetaDot, "phasePlotThetaThetaDot", "Phase plot of theta dot against theta");
}
/**
* Generates a time plot
*
* @param solution An object containing solution data.
* @return Nothing.
*/
function generateTimePlot(solution) {
// Generate time plot
genMultPlot(solution, ["x", "x dot", "theta", "theta dot"], "timePlot", "Plot of x, x dot, theta and theta dot against time");
}
/**
* Generate four plots:
* - The first is a phase plot of theta against x.
* - The second is a phase plot of x dot against x.
* - The third is a phase plot of theta dot against theta.
* - The fourth is a plot of x, x dot, theta and theta dot against time.
*
* @param objectOfInputs An object containing all the problem parameters.
* @return Nothing. Just generates the plots.
*/
function generatePlots(objectOfInputs) {
// Solve problem
var solution = solveProblem(RKF45, objectOfInputs);
// Plot solution
generateXThetaPhasePlot(solution);
generateXXDotPhasePlot(solution);
generateThetaThetaDotPhasePlot(solution);
generateTimePlot(solution);
}