How to make 'far away' markers appear smaller (perspective)
2 ビュー (過去 30 日間)
古いコメントを表示
To make it easier to visually interpret 3D data when shown on a 2D surface like the computer screen, I would like to plot data so that far-away markers appear smaller and nearby markers appear larger. Choosing the 'Perspective' axes projection seems to make no difference in marker size,
figure;
plot3(rand(1,10), rand(1,10), rand(1,10), 'ko')
ax = gca;
ax.Projection = 'perspective';
To me, all makers appear to be the same size here.

Next I tried making the markers actual 3D spheres. This works but it's fussy, and it still doesn't meet my aim of making it easier to read a 2D picture of a 3D plot,
nFace = 200; % Radius of sphere in plot units
[x,y,z] = sphere(nFace); % Create a sphere which we will replicate
sphereScale = 50; % Need to scale values so that spheres appear small, like markers
% xyz locations of sphere centers
xCenter = rand(1,10)*sphereScale - sphereScale/2;
yCenter = rand(1,10)*sphereScale - sphereScale/2;
zCenter = rand(1,10)*sphereScale - sphereScale/2;
% Plot the spheres/makers
figure;
for iSphere = 1:length(xCenter) % Plot several spheres
s(iSphere) = surf(x + xCenter(iSphere),...
y + yCenter(iSphere),...
z + zCenter(iSphere));
hold on;
end
axis equal;
% Make spheres appear like smooth 3D markers
set(s, 'facecolor', [1 1 1]*0.8, 'facealpha', 1, 'edgecolor', 'none', 'clipping','off');
ax = gca;
ax.Projection = 'perspective'; % This should result in foreshortening in the plot
view(30, 15);
% Add lighting to make spheres appear 3D
lightangle(-45,30)
h.FaceLighting = 'gouraud';
h.AmbientStrength = 0.3;
h.DiffuseStrength = 0.8;
h.SpecularStrength = 0.9;
h.SpecularExponent = 25;
h.BackFaceLighting = 'unlit';
I still can't tell which markers are 'nearer' and which are 'farther', though, so the 3D information in this plot is still hard to interpret visually.

0 件のコメント
採用された回答
Star Strider
2019 年 7 月 30 日
One option is to use a sort of ‘inverse square’ size dimension scaling function.
Example —
x = rand(1,10);
y = rand(1,10);
z = rand(1,10);
figure;
scatter3(x, y, z, 10./(x.^2 + y.^2), 'ko')
ax = gca;
ax.Projection = 'perspective';
This uses scatter3 because it offers a simple way to specify the marker sizes. (You could also include ‘z.^2’ in the scaling calculation, however I opted to use ‘x’ and ‘y’ only.)
Note that this only works for a fixed orientation with (0,0,1) the closest point. The marker sizes remain fixed, and do not scale appropriately as you rotate the axes. If your axes are different from the [0,1] range that rand provides, you willl also have to scale the distances appropriately.
2 件のコメント
Star Strider
2019 年 7 月 30 日
Thank you.
You can exaggerate it by increasing the power to which the vectors are raised, for example:
1./(x.^3 + y.^3)
There may be other nonlinear functions as well that will do this. I experimented with the ’inverse square’ idea simply to prove the concept.
その他の回答 (0 件)
参考
カテゴリ
Help Center および File Exchange で Surface and Mesh Plots についてさらに検索
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!