How to create bar chart with x axis labels as grouped for different data
31 views (last 30 days)
Show older comments
Hello all, I want to plot a bar chart in matlab. I have plotted it in excel and attached the image for reference:
I have attached the excel file also. Any clue on how to get this.
1 Comment
dpb
on 28 Aug 2023
<Shows up in Links>, might look at it for ideas.
Unfortunately, "ouf of the box", the MATLAB bar() function is limited.
Accepted Answer
Dave B
on 28 Aug 2023
Unfortunately MATLAB doesn't have a builtin feature for creating hierarchical rulers. An alternate workaround to the one dpb links to in the comment above is to use tiledlayout to make a separate axes for each bar chart. Here's an example that produces something somewhat similar to what you got in Excel:
tbl = readtable('Book1.xlsx','TextType','string');
%% This chunk fills in the rows in the table to match the top row for the section
for i = 2:height(tbl)
for j = 1:width(tbl)
if ismissing(tbl{i,j})
tbl{i,j} = tbl{i-1,j};
end
end
end
tbl.SolutionAlgorithm = categorical(tbl.SolutionAlgorithm, ["SIMPLE" "SIMPLEC" "COUPLED"]);
groups = unique(tbl.TurbulenceModels,'stable');
%%
% This layout will hold each of the axes
layout = tiledlayout(1,numel(groups),'TileSpacing','tight');
% A background axes serves to create the illusion that tall of the bar
% charts live in the same axes, in reality there will be one Axes for
% each group
backax=axes(layout);
backax.Layout.TileSpan=[1 numel(groups)];
for i = 1:numel(groups)
% Note: this code uses axes and then sets the tile rather than using
% the nexttile function. The latter would potentially target 'backax'
% on the first iteration
ax = axes(layout);
% Make a bar chart for each group:
ax.Layout.Tile = i;
ind1 = tbl.TurbulenceModels==groups(i) & tbl.MeshingModels=="Tetrahedral";
ind2 = tbl.TurbulenceModels==groups(i) & tbl.MeshingModels=="Hexcore";
x = [tbl.SolutionAlgorithm(ind1) tbl.SolutionAlgorithm(ind2)];
y = [tbl.Cd(ind1) tbl.Cd(ind2)];
bar(x, y, 'BaseValue', .4, 'EdgeColor', 'none')
% This uses the Tex interpreter to add line breaks to the group names,
% unforturnately this has the side effect of left-justifying the groups
xlabel(groups(i).replace(" ","\newline"))
% Toggle the visibility of the axes as a whole (the white background
% and both rulers) off, then toggle the visibility of just the x axis
% back on.
set(ax,'XTickLabelRotation',90,'YTick',[],'Visible','off','YLim',[.4 1],'TickDir','none')
ax.XAxis.Visible='on';
end
% Because the individual axes objects have their own x axis, it can be
% disabled on the background axes
backax.XAxis.Visible=false;
% set the background axes y limits to match the last axes created, and add
% a label.
ylim(backax, ylim(ax));
ylabel(backax,'Cd')
% A legend must be associated with an axes, but it can be positioned with
% respect to the layout as follows:
leg = legend(ax, ["Tetrahedral meshing" "Hexcore meshing"],"Orientation",'horizontal');
leg.Layout.Tile='north';
% Make the aspect ratio a little wider for this long x axis
f=gcf;f.Position(3)=f.Position(3)*1.4;
More Answers (0)
See Also
Categories
Find more on Data Distribution Plots in Help Center and File Exchange
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!