2011-08-21 12 views
6

Potrzebuję wykreślić listę 3d linii w Matlab. Jaki jest najszybszy sposób na zrobienie tego? Jestem obecnie robi coś podobnegoNajbardziej efektywny sposób narysować kilka linii 3d w Matlab

%edges is a MX2 matrix, holding the list of edges 
%points are the vertices' coordinates 
hold on; %so all the lines will be saved 
for i=1:size(edges,1) 
    a=edges(i,1); %get first point's index 
    b=edges(i,2); %get second point's index 
    p=[points(:,a) points(:,b)]; %construct a 3X2 matrix out of the 2 points 
    plot3(p(1,:),p(2,:),p(3,:)); %plot a line 
end 

Ale to nie tylko powolny podczas rzeczywistego pętli, ale także na końcu, uzyskany fabuła jest bardzo powolny i flegmatyczny, kiedy staram się, na przykład, obracać je za pomocą przeciągnij narzędzie obracania &.

Znam tę samą działkę przy użyciu OpenGL etc będzie działał znacznie szybciej ...

Odpowiedz

1

myślę, że można zrobić coś takiego (uwaga - mózg skompilowany kod ...)

figure; 
patch('faces', edges, 'vertices', points, 'edgecolor', 'b'); 
axis equal; 

Gdzie edges powinna być macierzą indeksów Nx2 i points powinna być macierzą współrzędnych Mx3 (transpozycja macierzy points).

Z mojego doświadczenia wynika, że ​​dzwonienie pod numer patch może być znacznie szybsze niż wielokrotne połączenia z numerem plot.

Aby dać pewne wyobrażenie, czasy wygenerować 1000 losowo wygenerowanych segmenty linii, wykorzystując mój MATLAB 7.1 przedstawiają się następująco (co prawda stary!):

  1. Wywołanie patch: 0.03 sekund.
  2. Wywołanie plot: 0,5 sekundy.

EDIT: Jednym ze sposobów, aby uzyskać zachowuje kolor krawędzi, jak chcesz (określenia pojedynczego koloru na krawędzi) jest wprowadzenie zduplikowane wierzchołki następująco:

Działa wokół problemu, który krawędzi kolor może być określony pośrednio poprzez dane koloru wierzchołków. Gdybyśmy polegali tylko na kolorach wierzchołków, wówczas wszystkie krawędzie dzielące wspólny wierzchołek mogą kończyć się kolorem przypisanym do tego wierzchołka - sprawdź "płaski" edgecolour opis:.

%% a "star" shape, so that we can really see what's going on 
%% with the edge colours!! 
pp = [0,0,0; 1,-1,0; 1,1,0; -1,1,0; -1,-1,0]; 
ee = [1,2; 1,3; 1,4; 1,5]; 

%% important - only 1 colour known per edge, not per vertex!! 
cc = (1:size(ee,1))'; 

%% setup a new set of vertices/edges/colours with duplicate vertices 
%% so that each edge gets it's correct colour 
nnum = 0; 
pnew = zeros(2 * size(ee, 1), 3); %% new vertices 
enew = zeros(1 * size(ee, 1), 2); %% new edge indices 
cnew = zeros(2 * size(ee, 1), 1); %% new edge colours - via vertices 
for j = 1 : size(ee, 1) 
    n1 = ee(j, 1); %% old edge indices 
    n2 = ee(j, 2); 
    enew(j, 1) = nnum + 1; %% new edge indicies into pnew 
    enew(j, 2) = nnum + 2; 
    pnew(nnum + 1, :) = pp(n1, :); %% create duplicate vertices 
    pnew(nnum + 2, :) = pp(n2, :); 
    cnew(nnum + 1) = cc(j); %% map single edge colour onto both vertices 
    cnew(nnum + 2) = cc(j); 
    nnum = nnum + 2; 
end 

%% Draw the set efficiently via patch 
tic 
figure; 
hold on; 
patch('faces', enew, 'vertices', pnew, 'facevertexcdata', cnew, ... 
    'edgecolor', 'flat', 'facecolor', 'none'); 
plot(pnew(:,1), pnew(:,2), 'b.'); 
axis equal; 
toc 

Byłoby ładniej jeśli MATLAB pozwalał bezpośrednio podać dane koloru krawędzi - ale to nie wydają się potwierdzać, że ...

nadzieję, że to pomaga.

+0

Dzięki! Czy jest szansa, że ​​możesz mi pokazać, w jaki sposób mogę wysłać tablicę kolorów, aby każda krawędź była zabarwiona innym kolorem? – olamundo

+0

@ nnoam: Istnieje kilka różnych opcji kolorowania, w zależności od tego, co chcesz. Możesz użyć parametru ''facevertexcdata'', aby ustawić interpolowane kolory z wierzchołków - wpisz' edit trimesh', aby uzyskać pomysł wzdłuż tych linii. Jeśli chciałeś tylko kilku płaskich kolorów ("b", "k", "r", itp.), To możesz podzielić krawędzie na kilka różnych grup i wybrać jeden kolor dla każdej grupy - zakładam tutaj masz o wiele więcej krawędzi niż kolorów. Mogą istnieć inne opcje - sprawdź dokumentację ... –

+0

Rzeczywiście muszę pokolorować każdą krawędź innym kolorem, z wielu kolorów (Powiedz, że pokazuję naprężenie wywierane na wszystkie belki wsporcze jakiejś struktury). Więc muszę określić kolor po krawędzi, a nie po wierzchołku, i nie mogę podzielić krawędzi na kilka różnych grup, ponieważ jest wiele kolorów ... – olamundo

6

Można użyć funkcji LINE niskim poziomie, przy użyciu NaN wykreślić jako odrębne segmenty:

%# sample graph vertices and edges (similar to your data) 
[adj,XYZ] = bucky; 
[r c] = find(adj); 
edges = [r c];  %# M-by-2 matrix holding the vertex indices 
points = XYZ';  %# 3-by-N matrix of points X/Y/Z coordinates 

%# build a list of separated lines 
e = edges'; 
e(end+1,:) = 1; 
e = e(:); 
p = points(:,e); 
p(:,3:3:end) = NaN; 

figure 
h = line(p(1,:), p(2,:), p(3,:)); 
view(3) 

Jest bardzo wydajny, gdyż tworzy pojedynczy obiekt liniowy.Teraz można dostosować linię, ale jest ona ograniczona mieć jeden kolor dla całego rzecz:

set(h, 'Color',[.4 .4 1], 'Marker','.', 'MarkerSize',10, ... 
    'MarkerFaceColor','g', 'MarkerEdgeColor','g') 

line


Według komentarzach, jeśli chcesz mieć każdą jego krawędź na wykresie w określonym kolorze, należy rozważyć poniższy kod. Polega ona na użyciu funkcji SURFACE:

p = p';      %'# transpose the above p for convenience 
clr = (1:size(p,1))';  %'# for each edge, color index in current colormap 
figure 
surface(p(:,[1 1]), p(:,[2 2]), p(:,[3 3]), [clr clr], ... 
    'EdgeColor','flat', 'FaceColor','none') 
colormap(hsv(numel(clr))) %# specify your colormap here 
view(3) 

surface

+0

Rozwiązanie "surface" jest najbliższe temu, o co go proszono, ale jeśli sprawdzisz http://www.mathworks.com/help/techdoc/ref/surface_props.html, to znowu wydaje się, że 'edgecolor' jest ustawiane tylko pośrednio przez dane koloru wierzchołka (implikuje to, że wszystkie krawędzie na twarz mają wspólny kolor wierzchołka o najniższym numerze), zamiast określać kolor dla każdej krawędzi bezpośrednio - czyli tego, co jest potrzebne. Opierając się na szybkiej kontroli, wydaje się, że daje to samo zachowanie, co rozwiązanie 'łatki'. Może coś przeoczyłem? –

Powiązane problemy