三次元で、ある座標からある座標に矢印を引きたいです。
Show older comments
質問のように、三次元空間で矢印を引きたいと考えています。
座標は一点ではなく、複数ある場合、それぞれの座標の始点と終点を結ぶ直線矢印を引いて、まとめて表したいです。
こちらにあるデータは、始点と終点の座標データのみです。
X, Y, Z軸の範囲も自動で設定できるようなプログラムもあれば◎です。
よろしくお願いします。
Answers (1)
Akira Agata
on 21 May 2018
quiver3 関数を使う以下の方法では如何でしょうか。
p0 = [0,0,0; 1,0,0; 0,1,0; 1,1,0]; % 始点の座標
p1 = [0,0,1; 1,0,1; 0,1,1; 1,1,1]; % 終点の座標
v = p1 - p0; % ベクトル
figure
quiver3(p0(:,1),p0(:,2),p0(:,3),v(:,1),v(:,2),v(:,3),0)

11 Comments
Haru Kame
on 21 May 2018
Akira Agata
on 21 May 2018
quiver3 関数の入力引数ですが、1~3番目は矢印の始点の x,y,z 座標を、4~6番目はベクトル(矢印)の x,y,z 成分を、それぞれ示しています。ちなみに、 quiver3 関数で複数のベクトルを描画する場合、ベクトルが重なり合わないように自動的にベクトルがスケーリングされてしまいます。このため上記のサンプルスクリプトでは、自動的なスケーリングをoffにするため、7番目の引数にゼロを設定しています。
quiver3 関数の詳細については、下記のヘルプページをご参照下さい。
Haru Kame
on 23 May 2018
Akira Agata
on 23 May 2018
データが200個の場合でも、forループを使わずに同様の方法で表示することができます。例えば 200個の始点のxyz座標と200個のベクトルを、それぞれ 200×3の配列として作成した場合は、下記のようになります。
% p: 始点の(x,y,z)座標×200個, v: 各始点に配置するベクトル
p = rand(200,3)*20;
v = ones(200,3)+rand(200,3);
figure
quiver3(p(:,1),p(:,2),p(:,3),v(:,1),v(:,2),v(:,3),0)

Haru Kame
on 27 May 2018
Akira Agata
on 29 May 2018
ご返信ありがとうございます。
p = rand(200,3)*20 についてですが、これは区間 (0,1) の一様乱数を200行3列の配列したうえで、各要素を20倍して p という変数に保存するという意味です。この1行を実行すると、MATLAB右側のワークスペースに、下記のような表示が出てくると思います。また、v = ones(200,3)+rand(200,3) は、要素がすべて1の200行3列の配列と、区間 (0,1) の一様乱数を要素とする200行3列の配列を足して v という変数に保存しています。
>エクセルファイルから読み込むようなことをしているのですが、その際に自動的に200×3の行列として読み込まれているのでしょうか。
読み込んだ後にワークスペースを見ることで確認できます。Excelファイルを読み込んだ後、下記の図と同様に値が 200x3 double、サイズが200x3、クラスが double の変数が2つ(p0, p1) 生成されていれば問題ありません。

Haru Kame
on 29 May 2018
Akira Agata
on 29 May 2018
修飾の内容にもよりますが、記載頂いた内容であれば scatter3 関数と組み合わせることで実現できます。例えば以前のサンプルコードに少し手を加えると、以下のようなプロットを生成できます。
% p: 始点の(x,y,z)座標×200個, v: 各始点に配置するベクトル
p = rand(200,3)*20;
v = ones(200,3)+rand(200,3);
markerSize = 30;
figure
quiver3(p(:,1),p(:,2),p(:,3),v(:,1),v(:,2),v(:,3),0)
hold on
scatter3(p(:,1),p(:,2),p(:,3),markerSize,p(:,3),'filled')
colorbar

Haru Kame
on 30 May 2018
Akira Agata
on 1 Jun 2018
Edited: Akira Agata
on 1 Jun 2018
各点のマーカーの色情報を保持しておいて、 scatter3 関数に引数として与えることで実現できます。例えば以下の例では、color という変数に初期状態での色情報 (ここでは初期状態における p の3列目の値) を保持しています。そのうえで、点の位置を更新した後、この変数を scatter3 関数の引数として与えることで、各点の位置が変わっても元の色で表示するようにしています。
% p: 始点の(x,y,z)座標×N個, v: 各始点に配置するベクトル
N = 50;
p = rand(N,3)*20;
p = sortrows(p,3,'descend'); % 3列目でソート
color = p(:,3);
v = ones(N,3)+rand(N,3);
markerSize = 30;
% 初期状態を表示
figure
quiver3(p(:,1),p(:,2),p(:,3),v(:,1),v(:,2),v(:,3),0)
hold on
scatter3(p(:,1),p(:,2),p(:,3),markerSize,color,'filled')
text(p(:,1),p(:,2),p(:,3),num2str((1:N)'))
view(-20,10)
title('Before')
h = colorbar;
h.Label.String = 'Initial value';
% 始点の位置を更新
p = rand(N,3)*20;
% 更新後の状態を表示(ただし各点の色は初期状態を維持)
figure
quiver3(p(:,1),p(:,2),p(:,3),v(:,1),v(:,2),v(:,3),0)
hold on
scatter3(p(:,1),p(:,2),p(:,3),markerSize,color,'filled')
text(p(:,1),p(:,2),p(:,3),num2str((1:N)'))
view(-20,10)
title('After')
h = colorbar;
h.Label.String = 'Initial value';


Haru Kame
on 4 Jun 2018
Categories
Find more on ベクトル場 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!