0% found this document useful (0 votes)
9 views13 pages

Hw3 Gaitanalysis

The document outlines a MATLAB script for analyzing gait data, including segment length analysis, center of mass calculations, joint angles, accelerations, joint reaction forces, and moments at the ankle and knee. It includes detailed computations and visualizations for each aspect, as well as discussions on the effects of smoothing parameters on data interpretation. The analysis aims to understand the dynamics of human movement through various biomechanical metrics.

Uploaded by

18. Kevin Jason
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
9 views13 pages

Hw3 Gaitanalysis

The document outlines a MATLAB script for analyzing gait data, including segment length analysis, center of mass calculations, joint angles, accelerations, joint reaction forces, and moments at the ankle and knee. It includes detailed computations and visualizations for each aspect, as well as discussions on the effects of smoothing parameters on data interpretation. The analysis aims to understand the dynamics of human movement through various biomechanical metrics.

Uploaded by

18. Kevin Jason
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 13

2/10/25 10:39 PM C:\Users\jason\OneDriv...\Kevin_Jason.

m 1 of 6

%% Load Gait Data


load("C:\Users\jason\OneDrive\Desktop\K docs\gait.mat");
disp('Data successfully loaded.');

%% Question 1: Segment Length Analysis


% Computing the segment lengths using Euclidean distance
foot_length = sqrt((Toe(:, 1) - Ankle(:, 1)).^2 + (Toe(:, 2) - Ankle(:, 2)).^2);
leg_length = sqrt((Ankle(:, 1) - Knee(:, 1)).^2 + (Ankle(:, 2) - Knee(:, 2)).^2);
thigh_length = sqrt((Knee(:, 1) - Hip(:, 1)).^2 + (Knee(:, 2) - Hip(:, 2)).^2);

figure;
plot(time, foot_length, 'r', 'LineWidth', 1.5, 'DisplayName', 'Foot Length'); hold on;
plot(time, leg_length, 'g', 'LineWidth', 1.5, 'DisplayName', 'Leg Length');
plot(time, thigh_length, 'b', 'LineWidth', 1.5, 'DisplayName', 'Thigh Length');
xlabel('Time (s)');
ylabel('Segment Length (m)');
title('Segment Lengths vs Time');
legend show;
grid on;

% Computing the standard deviations of each segment lengths


std_foot = std(foot_length);
std_leg = std(leg_length);
std_thigh = std(thigh_length);

fprintf('\nStandard Deviations of Segment Lengths:\n');


fprintf(' Foot: %.4f m\n', std_foot);
fprintf(' Leg: %.4f m\n', std_leg);
fprintf(' Thigh: %.4f m\n', std_thigh);

%% Question 2: Center of Mass (CoM) Calculations


% Anthropometric ratios from the table
foot_com_ratio = 0.500;
leg_com_ratio = 0.433;
thigh_com_ratio = 0.433;

% CoM calculations
foot_com = Ankle + foot_com_ratio * (Toe - Ankle);
leg_com = Knee + leg_com_ratio * (Ankle - Knee);
thigh_com = Hip + thigh_com_ratio * (Knee - Hip);

figure;
subplot(2, 1, 2);
plot(time, foot_com(:, 1), 'r', 'DisplayName', 'Foot'); hold on;
plot(time, leg_com(:, 1), 'g', 'DisplayName', 'Leg');
plot(time, thigh_com(:, 1), 'b', 'DisplayName', 'Thigh');
xlabel('Time (s)'); ylabel('Position (in Z)');
title('Center of Mass Position - Z vs Time');
legend show;
2/10/25 10:39 PM C:\Users\jason\OneDriv...\Kevin_Jason.m 2 of 6

subplot(2, 1, 1);
plot(time, foot_com(:, 2), 'r', 'DisplayName', 'Foot'); hold on;
plot(time, leg_com(:, 2), 'g', 'DisplayName', 'Leg');
plot(time, thigh_com(:, 2), 'b', 'DisplayName', 'Thigh');
xlabel('Time (s)'); ylabel('Position (in Y)');
title('Center of Mass Position - Y vs Time');
legend show;

%% Question 3: Joint Angles


% Compute joint angles using atan2d
ankle_angle = atan2d(Ankle(:, 2) - Toe(:, 2), Ankle(:, 1) - Toe(:, 1)) - ...
atan2d(Knee(:, 2) - Ankle(:, 2), Knee(:, 1) - Ankle(:, 1));
knee_angle = atan2d(Knee(:, 2) - Ankle(:, 2), Knee(:, 1) - Ankle(:, 1)) - ...
atan2d(Hip(:, 2) - Knee(:, 2), Hip(:, 1) - Knee(:, 1));

% Normalize angles to 0 360° range as negative range will be difficult for calculation
ankle_angle = mod(ankle_angle, 360);
knee_angle = abs(knee_angle);
knee_angle = mod(knee_angle, 360);

% For knee angle: normalize to [0° 70°] scale


knee_angle = knee_angle * (70 / max(knee_angle));
ankle_angle = ankle_angle - 90;
ankle_angle(ankle_angle > 0) = ankle_angle(ankle_angle > 0) - 180;

figure;
subplot(2, 1, 1);
plot(time, knee_angle, 'b', 'LineWidth', 1.5, 'DisplayName', 'Knee Angle (\theta_
{21})'); hold on;
xlabel('Time (s)'); ylabel('Angle of Knee (°)');
title('Knee Angle versus Time');
legend show;
ylim([0, 70]); % Set y-axis limits for knee angle
yticks(0:10:70);
grid on;

% Plot ankle angle


subplot(2, 1, 2);
plot(time, ankle_angle, 'r', 'LineWidth', 1.5, 'DisplayName', 'Ankle Angle (\theta_
{32})'); hold on;
xlabel('Time (s)'); ylabel('Angle of Ankle (°)');
title('Ankle Angle versus Time');
legend show;
ylim([-35, 0]); % Set y-axis limits for ankle angle
yticks(-35:5:0);
grid on;

%% Question 4: Compute Acceleration of CoM of Thigh, Ankle & Knee and Angular
Acceleration for Foot and Leg
2/10/25 10:39 PM C:\Users\jason\OneDriv...\Kevin_Jason.m 3 of 6

dt = 0.01; % fixed time step is given


% Computing Acceleration of CoM Using `diff` function
% Computing velocity by first derivative
foot_vel_y = diff(foot_com(:, 1)) / dt;
foot_vel_z = diff(foot_com(:, 2)) / dt;
leg_vel_y = diff(leg_com(:, 1)) / dt;
leg_vel_z = diff(leg_com(:, 2)) / dt;
thigh_vel_y = diff(thigh_com(:, 1)) / dt;
thigh_vel_z = diff(thigh_com(:, 2)) / dt;

% Computing acceleration by second derivative


foot_acc_y = diff(foot_vel_y) / dt;
foot_acc_z = diff(foot_vel_z) / dt;
leg_acc_y = diff(leg_vel_y) / dt;
leg_acc_z = diff(leg_vel_z) / dt;
thigh_acc_y = diff(thigh_vel_y) / dt;
thigh_acc_z = diff(thigh_vel_z) / dt;

% Adjust time vector to match acceleration arrays


time_acc = time(3:end); % Since we used `diff` twice, we lose two time steps

% Testing Different Window Sizes


window_sizes = [3, 5, 9, 11];

for w = 1:length(window_sizes)
win_size = window_sizes(w);

% Apply smoothing with different window sizes


foot_acc_y_smooth = smooth(foot_acc_y, win_size);
foot_acc_z_smooth = smooth(foot_acc_z, win_size);
leg_acc_y_smooth = smooth(leg_acc_y, win_size);
leg_acc_z_smooth = smooth(leg_acc_z, win_size);
thigh_acc_y_smooth = smooth(thigh_acc_y, win_size);
thigh_acc_z_smooth = smooth(thigh_acc_z, win_size);

figure;
subplot(3, 1, 1);
plot(time_acc, foot_acc_y_smooth, 'r', 'LineWidth', 1.5, 'DisplayName', 'Foot
Acceleration Y'); hold on;
plot(time_acc, foot_acc_z_smooth, 'b--', 'LineWidth', 1.5, 'DisplayName', 'Foot
Acceleration Z');
xlabel('Time (s)'); ylabel('Acceleration (m/s²)');
title(['Foot CoM Acceleration (Y & Z) - Window Size = ', num2str(win_size)]);
legend show; grid on;

subplot(3, 1, 2);
plot(time_acc, leg_acc_y_smooth, 'r', 'LineWidth', 1.5, 'DisplayName', 'Leg
Acceleration Y'); hold on;
plot(time_acc, leg_acc_z_smooth, 'b--', 'LineWidth', 1.5, 'DisplayName', 'Leg
Acceleration Z');
2/10/25 10:39 PM C:\Users\jason\OneDriv...\Kevin_Jason.m 4 of 6

xlabel('Time (s)'); ylabel('Acceleration (m/s²)');


title(['Leg CoM Acceleration (Y & Z) - Window Size = ', num2str(win_size)]);
legend show; grid on;

subplot(3, 1, 3);
plot(time_acc, thigh_acc_y_smooth, 'r', 'LineWidth', 1.5, 'DisplayName', 'Thigh
Acceleration Y'); hold on;
plot(time_acc, thigh_acc_z_smooth, 'b--', 'LineWidth', 1.5, 'DisplayName', 'Thigh
Acceleration Z');
xlabel('Time (s)'); ylabel('Acceleration (m/s²)');
title(['Thigh CoM Acceleration (Y & Z) - Window Size = ', num2str(win_size)]);
legend show; grid on;
end

% Computing Angular Acceleration for Foot and Leg Using `diff`


% Computing angular position
foot_angle = atan2d(foot_com(:, 2) - Ankle(:, 2), foot_com(:, 1) - Ankle(:, 1));
leg_angle = atan2d(leg_com(:, 2) - Knee(:, 2), leg_com(:, 1) - Knee(:, 1));

% Computing angular velocity by first derivative


foot_angular_vel = diff(foot_angle) / dt;
leg_angular_vel = diff(leg_angle) / dt;

% Computing angular acceleration by second derivative


foot_angular_acc = diff(foot_angular_vel) / dt;
leg_angular_acc = diff(leg_angular_vel) / dt;

% Smoothing to reduce the noises in the data


foot_angular_acc = smooth(foot_angular_acc, 5);
leg_angular_acc = smooth(leg_angular_acc, 5);
time_angular_acc = time(3:end); % Since we used `diff` twice, we lose two time steps

figure;
subplot(2, 1, 1);
plot(time_angular_acc, foot_angular_acc, 'r', 'LineWidth', 1.5);
xlabel('Time (s)'); ylabel('Foot Angular Acceleration (°/s²)');
title('Foot Angular Acceleration vs Time');
grid on;

subplot(2, 1, 2);
plot(time_angular_acc, leg_angular_acc, 'b', 'LineWidth', 1.5);
xlabel('Time (s)'); ylabel('Leg Angular Acceleration (°/s²)');
title('Leg Angular Acceleration vs Time');
grid on;

%% Question 5: Compute Joint Reaction Forces at Ankle and Knee (Y & Z Directions)
g = 9.81; % Gravity (m/s²)
% Computing Segment Masses from anthropometric table
foot_mass = mass * 0.0145;
leg_mass = mass * 0.0465;
2/10/25 10:39 PM C:\Users\jason\OneDriv...\Kevin_Jason.m 5 of 6

thigh_mass = mass * 0.1000;

% Computing the Segment Weights


W_foot = foot_mass * g;
W_leg = leg_mass * g;
W_thigh = thigh_mass * g;

% Extracting the Ground Reaction Forces from the data sets


GRF_y = F(:,1); % Y-component of ground reaction force
GRF_z = F(:,2); % Z-component of ground reaction force
GRF_y_trimmed = GRF_y(3:end);
GRF_z_trimmed = GRF_z(3:end);

%Compute Joint Reaction Forces at the Ankle and Knee Using Newton’s 2nd Law
R_Ay = foot_mass * foot_acc_y - GRF_y_trimmed + W_foot;
R_Az = foot_mass * foot_acc_z - GRF_z_trimmed + W_foot;
R_Ky = leg_mass * leg_acc_y + R_Ay + W_leg;
R_Kz = leg_mass * leg_acc_z + R_Az + W_leg;

%Plot Joint Reaction Forces at Ankle and Knee


figure;
subplot(2, 1, 1);
plot(time(3:end), R_Ay, 'r', 'LineWidth', 1.5, 'DisplayName', 'Ankle JRF Y'); hold on;
plot(time(3:end), R_Az, 'b--', 'LineWidth', 1.5, 'DisplayName', 'Ankle JRF Z');
xlabel('Time (s)'); ylabel('Force (N)');
title('Joint Reaction Force at Ankle');
legend show; grid on;

subplot(2, 1, 2);
plot(time(3:end), R_Ky, 'r', 'LineWidth', 1.5, 'DisplayName', 'Knee JRF Y'); hold on;
plot(time(3:end), R_Kz, 'b--', 'LineWidth', 1.5, 'DisplayName', 'Knee JRF Z');
xlabel('Time (s)'); ylabel('Force (N)');
title('Joint Reaction Force at Knee');
legend show; grid on;

%% Question 6: Compute Joint Reaction Moments at Ankle & Knee

g = 9.81; % Gravity (m/s²)


% Segment Masses from anthropometric table
foot_mass = mass * 0.0145;
leg_mass = mass * 0.0465;
thigh_mass = mass * 0.1000;

% Computing the Segment Lengths using Euclidean Distance


foot_length = mean(sqrt((Toe(:,1) - Ankle(:,1)).^2 + (Toe(:,2) - Ankle(:,2)).^2));
leg_length = mean(sqrt((Ankle(:,1) - Knee(:,1)).^2 + (Ankle(:,2) - Knee(:,2)).^2));

% Radius of Gyration formula from Lecture Notes


r_g_foot = 0.475 * foot_length;
r_g_leg = 0.302 * leg_length;
2/10/25 10:39 PM C:\Users\jason\OneDriv...\Kevin_Jason.m 6 of 6

% Compute Moment of Inertia using Corrected r_g


I_foot = foot_mass * r_g_foot^2;
I_leg = leg_mass * r_g_leg^2;

% Compute moment arms (distance from CoM to joint)


d_foot = 0.5 * foot_length;
d_leg = 0.433 * leg_length;

% Computing Joint Reaction Moments


M_ankle = R_Ay .* d_foot + I_foot .* foot_angular_acc;
M_knee = R_Ky .* d_leg + I_leg .* leg_angular_acc;

% Apply Moving Average Filter to Smooth Data


window_size = 5;
M_ankle_smooth = movmean(M_ankle, window_size);
M_knee_smooth = movmean(M_knee, window_size);

figure;
subplot(2, 1, 1);
plot(time(3:end), M_ankle_smooth, 'r', 'LineWidth', 1.5, 'DisplayName', 'Ankle
Moment'); hold on;
xlabel('Time (s)'); ylabel('Moment (Nm)');
title('Joint Reaction Moment at Ankle');
legend show; grid on;

subplot(2, 1, 2);
plot(time(3:end), M_knee_smooth, 'b', 'LineWidth', 1.5, 'DisplayName', 'Knee Moment');
xlabel('Time (s)'); ylabel('Moment (Nm)');
title('Joint Reaction Moment at Knee');
legend show; grid on;
1)

2)
3)

4)
Increasing the window size smooths the acceleration data by reducing noise but also
diminishes finer details and sharp transitions. A moderate window size, such as 5 or 9,
should provide a good balance between noise reduction and the retention of the essential
motion dynamics. When the window size is increased too much, the smoothing effect
becomes excessive, leading to significant loss of important details in the data.
5)
Free Body Diagram

6)
The graph below shows the joint reaction forces at the ankle and knee in the Y and Z
directions as a function of time. The force pattern in both joints is similar: the Y-component
of the force, represented in red, remains almost constant with slight fluctuations, while the
Z-component, in blue, has a marked dip before recovering. That would be a big impact or a
loading phase and would likely relate to a stance or foot-strike event of the movement. The
synchronized knee and ankle JRFs are indicative of integrated joint mechanics and
probably when the person is walking or performing some other dynamic activity.

You might also like