stewart-simscape/kinematic-study.org

185 lines
6.3 KiB
Org Mode
Raw Normal View History

#+TITLE: Kinematic Study of the Stewart Platform
:DRAWER:
#+HTML_LINK_HOME: ./index.html
#+HTML_LINK_UP: ./index.html
#+HTML_HEAD: <link rel="stylesheet" type="text/css" href="./css/htmlize.css"/>
#+HTML_HEAD: <link rel="stylesheet" type="text/css" href="./css/readtheorg.css"/>
#+HTML_HEAD: <script src="./js/jquery.min.js"></script>
#+HTML_HEAD: <script src="./js/bootstrap.min.js"></script>
#+HTML_HEAD: <script src="./js/jquery.stickytableheaders.min.js"></script>
#+HTML_HEAD: <script src="./js/readtheorg.js"></script>
#+PROPERTY: header-args:matlab :session *MATLAB*
#+PROPERTY: header-args:matlab+ :tangle matlab/kinematic_study.m
#+PROPERTY: header-args:matlab+ :comments org
#+PROPERTY: header-args:matlab+ :exports both
#+PROPERTY: header-args:matlab+ :results none
#+PROPERTY: header-args:matlab+ :eval no-export
#+PROPERTY: header-args:matlab+ :noweb yes
#+PROPERTY: header-args:matlab+ :mkdirp yes
#+PROPERTY: header-args:matlab+ :output-dir figs
:END:
2020-01-22 15:32:32 +01:00
* Matlab Init :noexport:ignore:
#+begin_src matlab :tangle no :exports none :results silent :noweb yes :var current_dir=(file-name-directory buffer-file-name)
<<matlab-dir>>
#+end_src
#+begin_src matlab :exports none :results silent :noweb yes
<<matlab-init>>
2020-01-22 15:32:32 +01:00
#+end_src
#+begin_src matlab :results none :exports none
simulinkproject('./');
#+end_src
* Needed Actuator Stroke
The goal is to determine the needed stroke of the actuators to obtain wanted translations and rotations.
** Stewart architecture definition
We use a cubic architecture.
#+begin_src matlab :results silent
opts = struct(...
'H_tot', 90, ... % Total height of the Hexapod [mm]
'L', 200/sqrt(3), ... % Size of the Cube [mm]
'H', 60, ... % Height between base joints and platform joints [mm]
'H0', 200/2-60/2 ... % Height between the corner of the cube and the plane containing the base joints [mm]
);
stewart = initializeCubicConfiguration(opts);
opts = struct(...
'Jd_pos', [0, 0, 100], ... % Position of the Jacobian for displacement estimation from the top of the mobile platform [mm]
'Jf_pos', [0, 0, -50] ... % Position of the Jacobian for force location from the top of the mobile platform [mm]
);
stewart = computeGeometricalProperties(stewart, opts);
opts = struct(...
'stroke', 50e-6 ... % Maximum stroke of each actuator [m]
);
stewart = initializeMechanicalElements(stewart, opts);
save('./mat/stewart.mat', 'stewart');
#+end_src
** Wanted translations and rotations
We define wanted translations and rotations
#+begin_src matlab :results silent
Tx_max = 15e-6; % Translation [m]
Ty_max = 15e-6; % Translation [m]
Tz_max = 15e-6; % Translation [m]
Rx_max = 30e-6; % Rotation [rad]
Ry_max = 30e-6; % Rotation [rad]
#+end_src
** Needed stroke for "pure" rotations or translations
First, we estimate the needed actuator stroke for "pure" rotations and translation.
#+begin_src matlab :results silent
LTx = stewart.Jd*[Tx_max 0 0 0 0 0]';
LTy = stewart.Jd*[0 Ty_max 0 0 0 0]';
LTz = stewart.Jd*[0 0 Tz_max 0 0 0]';
LRx = stewart.Jd*[0 0 0 Rx_max 0 0]';
LRy = stewart.Jd*[0 0 0 0 Ry_max 0]';
#+end_src
#+begin_src matlab :results value :exports results
ans = sprintf('From %.2g[m] to %.2g[m]: Total stroke = %.1f[um]', min(min([LTx,LTy,LTz,LRx,LRy])), max(max([LTx,LTy,LTz,LRx,LRy])), 1e6*(max(max([LTx,LTy,LTz,LRx,LRy]))-min(min([LTx,LTy,LTz,LRx,LRy]))))
#+end_src
#+RESULTS:
: From -1.2e-05[m] to 1.1e-05[m]: Total stroke = 22.9[um]
** Needed stroke for combined translations and rotations
Now, we combine translations and rotations, and we try to find the worst case (that we suppose to happen at the border).
#+begin_src matlab :results none
Lmax = 0;
Lmin = 0;
pos = [0, 0, 0, 0, 0];
for Tx = [-Tx_max,Tx_max]
for Ty = [-Ty_max,Ty_max]
for Tz = [-Tz_max,Tz_max]
for Rx = [-Rx_max,Rx_max]
for Ry = [-Ry_max,Ry_max]
lmax = max(stewart.Jd*[Tx Ty Tz Rx Ry 0]');
lmin = min(stewart.Jd*[Tx Ty Tz Rx Ry 0]');
if lmax > Lmax
Lmax = lmax;
pos = [Tx Ty Tz Rx Ry];
end
if lmin < Lmin
Lmin = lmin;
end
end
end
end
end
end
#+end_src
We obtain a needed stroke shown below (almost two times the needed stroke for "pure" rotations and translations).
#+begin_src matlab :results value :exports results
ans = sprintf('From %.2g[m] to %.2g[m]: Total stroke = %.1f[um]', Lmin, Lmax, 1e6*(Lmax-Lmin))
#+end_src
#+RESULTS:
: From -3.1e-05[m] to 3.1e-05[m]: Total stroke = 61.5[um]
* Maximum Stroke
From a specified actuator stroke, we try to estimate the available maneuverability of the Stewart platform.
#+begin_src matlab :results silent
[X, Y, Z] = getMaxPositions(stewart);
#+end_src
#+begin_src matlab :results silent
figure;
plot3(X, Y, Z, 'k-')
#+end_src
* Functions
:PROPERTIES:
:HEADER-ARGS:matlab+: :exports code
:HEADER-ARGS:matlab+: :comments no
:HEADER-ARGS:matlab+: :mkdir yes
:HEADER-ARGS:matlab+: :eval no
:END:
** getMaxPositions
:PROPERTIES:
:HEADER-ARGS:matlab+: :tangle src/getMaxPositions.m
:END:
#+begin_src matlab
function [X, Y, Z] = getMaxPositions(stewart)
Leg = stewart.Leg;
J = stewart.Jd;
theta = linspace(0, 2*pi, 100);
phi = linspace(-pi/2 , pi/2, 100);
dmax = zeros(length(theta), length(phi));
for i = 1:length(theta)
for j = 1:length(phi)
L = J*[cos(phi(j))*cos(theta(i)) cos(phi(j))*sin(theta(i)) sin(phi(j)) 0 0 0]';
dmax(i, j) = Leg.stroke/max(abs(L));
end
end
X = dmax.*cos(repmat(phi,length(theta),1)).*cos(repmat(theta,length(phi),1))';
Y = dmax.*cos(repmat(phi,length(theta),1)).*sin(repmat(theta,length(phi),1))';
Z = dmax.*sin(repmat(phi,length(theta),1));
end
#+end_src
** getMaxPureDisplacement
:PROPERTIES:
:HEADER-ARGS:matlab+: :tangle src/getMaxPureDisplacement.m
:END:
#+begin_src matlab
function [max_disp] = getMaxPureDisplacement(Leg, J)
max_disp = zeros(6, 1);
max_disp(1) = Leg.stroke/max(abs(J*[1 0 0 0 0 0]'));
max_disp(2) = Leg.stroke/max(abs(J*[0 1 0 0 0 0]'));
max_disp(3) = Leg.stroke/max(abs(J*[0 0 1 0 0 0]'));
max_disp(4) = Leg.stroke/max(abs(J*[0 0 0 1 0 0]'));
max_disp(5) = Leg.stroke/max(abs(J*[0 0 0 0 1 0]'));
max_disp(6) = Leg.stroke/max(abs(J*[0 0 0 0 0 1]'));
end
#+end_src