# How to create a custom profile in matlab plots

56 Ansichten (letzte 30 Tage)
Sachin Hegde am 24 Jul. 2024 um 14:56
Bearbeitet: Umar am 25 Jul. 2024 um 18:23
Hello Everyone,
I am trying to create a profile based on user defined inputs. The profile consists of different modes each having a certain duration and order as defined by the user.
I have uploaded a picture which shows how i want the profile to look like.
Additionally i have coded to some extent, but i am struggling to get it right.
Also i would like to break the number of cycles for dynamic elements and use '...' to show continuity. However, on th etime axis i would like to have the actual value instead of shortened periods by discontinuity.
I kindly request for support and i thank you in advance.
Vconst.val = [1, 0.85, 0.6, 0.4];
Vconst.txt = {'OCV', 'Idle', 'Mid Load', 'High Load'};
Vdyn.val = [0.8, 0.7, 0.8, 0.5, 1.5, 1];
Vdyn.txt = {'Dynamic Low', 'Dyn low trough', 'Dynamic High', 'Dyn high trough', 'SUSD', 'SUSD trough'};
% Define the order of phases and durations
order = {'OCV', 'SUSD', 'OCV', 'Mid Load', 'High Load', 'Mid Load', 'Dynamic Low', 'Mid Load', 'Dynamic High', 'OCV'}; % duration in s for Vconst elements, nr. of cycles for Vdyn elements
durations = [100, 10, 200, 100, 50, 50, 4, 50, 4, 100]; % Corresponding durations in seconds or cycles
% Initialize time and voltage vectors
time = [];
voltage = [];
current_time = 0;
% Generate time and voltage vectors
for i = 1:length(order)
phase = order{i};
duration = durations(i);
t = current_time + (0:0.1:duration);
if ismember(phase, {'OCV', 'Idle', 'Mid Load', 'High Load'})
% Constant phases
t = current_time + (0:0.1:duration);
V_idx = find(strcmp(Vconst.txt, phase));
v = Vconst.val(V_idx) * ones(size(t));
time_act(i) = t(end);
else
% Dynamic phases
n_cycles = duration; % Number of dynamic cycles
t_dynamic_full = [];
v_dynamic_full = [];
Vdyn_idx = find(strcmp(Vdyn.txt, phase));
peak_height = Vdyn.val(Vdyn_idx);
trough_height = Vdyn.val(Vdyn_idx + 1);
nr_pts = 50;
for j = 1:n_cycles
t_cycle = current_time + (0:1:nr_pts);
tri_wave = sawtooth(2 * pi * (1/nr_pts) * (t_cycle - current_time), 0.5);
tri_wave = (peak_height - trough_height) * tri_wave / 2 + (peak_height + trough_height) / 2;
tri_wave(tri_wave > peak_height) = peak_height;
tri_wave(tri_wave < trough_height) = trough_height;
t_dynamic_full = [t_dynamic_full, t_cycle];
v_dynamic_full = [v_dynamic_full, tri_wave];
current_time = t_cycle(end);
end
time_act(i) = t_dynamic_full(end);
if n_cycles > 3
t_dynamic_1 = t_dynamic_full(1:nr_pts*2+2);
v_dynamic_1 = v_dynamic_full(1:nr_pts*2+2);
t_dynamic_2 = t_dynamic_full(nr_pts*3+3:nr_pts*4+4);
v_dynamic_2 = v_dynamic_full(nr_pts*3+3:nr_pts*4+4);
t_continuity = t_dynamic_full(nr_pts*2+4:nr_pts*3+2);
v_continuity = NaN * ones(size(t_continuity));
t = [t_dynamic_1, t_continuity, t_dynamic_2];
v = [v_dynamic_1, v_continuity, v_dynamic_2];
else
t = t_dynamic_full;
v = v_dynamic_full;
end
end
time = [time, t];
voltage = [voltage, v];
current_time = t(end);
if i>1
time_act(i) = time_act(i)+time_act(i-1);
else
end
end
% Plot the voltage over time
figure;
plot(time, voltage, 'LineWidth', 1.5);
xlabel('Time (s)');
ylabel('Voltage (V)');
title('User Defined Plot with Flexible Phase Order and Durations');
grid on;
ylim([0 2])
yticklabels([])
##### 3 Kommentare1 älteren Kommentar anzeigen1 älteren Kommentar ausblenden
Sachin Hegde am 25 Jul. 2024 um 8:54
Hello Umar,
First of all thank you. But i think there was some misunderstanding. For the dynamic cycles i do not want to have all the cycles shown (attached figure in the original post shows how i want it). I want to only show 2 cycles followed by '...' and finally the last cycle (something like this ^^...^). I need time axis to just show the values at the end of each phase.
Umar am 25 Jul. 2024 um 18:17
Bearbeitet: Umar am 25 Jul. 2024 um 18:23

Hi Sachin,

I spent time by updating your code by showing values at end of each phase and to check if there are more than 2 cycles for the last dynamic phase. However, I left all cycles shown on purpose for you to figure out rest of the code snippet and figure out adding lines of code for 2 cycles followed by '...' and finally the last cycle (something like this ^^...^ because if I do all the work, you will not be able to learn a lot about your project. In my opinion, you were looking for clues and were struggling figuring it out. Hope, I did help you out figuring out most things. Here is the updated code along with attached plot.

Vconst.val = [1, 0.85, 0.6, 0.4];

Vconst.txt = {'OCV', 'Idle', 'Mid Load', 'High Load'};

Vdyn.val = [0.8, 0.7, 0.8, 0.5, 1.5, 1];

Vdyn.txt = {'Dynamic Low', 'Dyn low trough', 'Dynamic High', 'Dyn high trough', 'SUSD', 'SUSD trough'};

% Define the order of phases and durations

order = {'OCV', 'SUSD', 'OCV', 'Mid Load', 'High Load', 'Mid Load', 'Dynamic Low', 'Mid Load', 'Dynamic High', 'OCV'}; % duration in s for Vconst elements, nr. of cycles for Vdyn elements

durations = [100, 10, 200, 100, 50, 50, 4, 50, 4, 100]; % Corresponding durations in seconds or cycles

% Initialize time and voltage vectors

time = [];

voltage = [];

current_time = 0;

% Generate time and voltage vectors

for i = 1:length(order)

`    phase = order{i};`
`    duration = durations(i);`
`    if ismember(phase, {'OCV', 'Idle', 'Mid Load', 'High Load'})`
`        % Constant phases`
`        t = current_time + (0:0.1:duration);`
`        V_idx = find(strcmp(Vconst.txt, phase));`
`        v = Vconst.val(V_idx) * ones(size(t));`
`        time_act(i) = t(end);`
`    else`
`        % Dynamic phases`
`        n_cycles = duration;  % Number of dynamic cycles`
`        t_dynamic_full = [];`
`        v_dynamic_full = [];`
`        Vdyn_idx = find(strcmp(Vdyn.txt, phase));`
`        peak_height = Vdyn.val(Vdyn_idx);`
`        trough_height = Vdyn.val(Vdyn_idx + 1);`
`        nr_pts = 50;`
`        % Calculate the number of breaks needed based on the number of cycles`
`        n_breaks = n_cycles - 1;`
`        for j = 1:n_cycles`
`            t_cycle = current_time + (0:1:nr_pts);`
`            tri_wave = sawtooth(2 * pi * (1/nr_pts) * (t_cycle - current_time), 0.5);`
`            tri_wave = (peak_height - trough_height) * tri_wave / 2 + (peak_height + trough_height) / 2;`
`            tri_wave(tri_wave > peak_height) = peak_height;`
`            tri_wave(tri_wave < trough_height) = trough_height;`
`            t_dynamic_full = [t_dynamic_full, t_cycle];`
`            v_dynamic_full = [v_dynamic_full, tri_wave];`
```            current_time = t_cycle(end);
end```
`        time_act(i) = t_dynamic_full(end);`
`        % Check if breaks are needed`
`        if n_breaks > 0`
`            % Calculate the number of points per break`
`            nr_pts_per_break = floor(nr_pts / (n_breaks + 1));`
`            % Initialize arrays for breaks`
`            t_breaks = [];`
`            v_breaks = [];`
`            % Generate breaks`
```            for k = 1:n_breaks
t_break = current_time + (0:1:nr_pts_per_break);```
`                v_break = NaN * ones(size(t_break));`
`                t_breaks = [t_breaks, t_break];`
`                v_breaks = [v_breaks, v_break];`
```                current_time = t_break(end);
end
% Combine the dynamic phases and breaks```
`            t = [t_dynamic_full(1:nr_pts_per_break+1), t_breaks, t_dynamic_full(nr_pts_per_break+2:end)];`
`            v = [v_dynamic_full(1:nr_pts_per_break+1), v_breaks, v_dynamic_full(nr_pts_per_break+2:end)];`
`        else`
`            % No breaks needed, use the full dynamic waveform`
`            t = t_dynamic_full;`
`            v = v_dynamic_full;`
`        end`
`    end`
`    time = [time, t + current_time];`
`    voltage = [voltage, v];`
`    current_time = current_time + duration;`
`    if i > 1`
`        time_act(i) = time_act(i) + time_act(i-1);`
`    end`

end

% Plot the voltage over time

figure;

plot(time, voltage, 'LineWidth', 1.5);

xlabel('Time (s)');

ylabel('Voltage (V)');

title('User Defined Plot with Flexible Phase Order and Durations');

grid on;

ylim([0 2])

yticklabels([])

% Modify time axis to show values at the end of each phase

xticks(time_act);

xticklabels(order);

xtickangle(45);

% Check if there are more than 2 cycles for the last dynamic phase

last_cycle_idx = find(strcmp(order, 'OCV'), 1, 'last');

if last_cycle_idx < length(time_act)

`    last_cycle_start = time_act(last_cycle_idx);`
`    last_cycle_end = time_act(last_cycle_idx + 1);`
`    last_cycle_duration = last_cycle_end - last_cycle_start;`
`    last_cycle_ticks = linspace(last_cycle_start, last_cycle_end, last_cycle_duration * 10 + 1);`
```    last_cycle_labels = repmat('^', 1, last_cycle_duration * 10 + 1);
xticks([xticks(1:2), last_cycle_ticks]);```
`    xticklabels([xticklabels(1:2), '...', last_cycle_labels]);`

end

Please let me know if you have any further questions. I really enjoyed working on this project and learned something about ticklabels how useful they can be especially for this project. Hope, no hard feelings.

Melden Sie sich an, um zu kommentieren.

### Kategorien

Mehr zu Image Data Workflows finden Sie in Help Center und File Exchange

R2024a

### Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by