我想創建一個函數,用Irrlicht引擎在空間中定位一個自由浮動的二維光柵圖像。靈感來自於R package rgl中的函數rgl::show2d。 R中的示例實現可以找到here。Irrlicht:基於四個角座標在三維空間中繪製二維圖像
輸入數據應當被限制於路徑圖像和與各情節矩形的四個角的座標的表格。
我的第一個,相當原始和最終失敗的方式與Irrlicht的認識到這一點:
創建一個立方體:
ISceneNode * picturenode = scenemgr->addCubeSceneNode();
拼合一面:
picturenode->setScale(vector3df(1, 0.001, 1));
添加圖片作爲紋理:
picturenode->setMaterialTexture(0, driver->getTexture("path/to/image.png"));
將展平立方體放置在四個角座標的中心位置。我只用一個小函數position_calc()
來計算所有三個軸上的平均座標。
vector3df position = position_calc(rcdf); picturenode->setPosition(position);
通過計算正常由四個角落的座標限定的平面的,歸一化的結果,並試圖以某種方式翻譯所得的矢量來旋轉角度確定對象的旋轉。
vector3df normal = normal_calc(rcdf);
vector3df angles = (normal.normalize()).getSphericalCoordinateAngles();
picturenode->setRotation(angles);
此解決方案不會產生預期結果。旋轉計算錯誤。採用這種方法,我也無法正確地將圖像縮放到角點座標。
我該如何解決我的工作流程?或者有沒有更好的方法來實現Irrlicht,我不知道?
編輯:感謝@spug我相信,我幾乎沒有。我試圖實施他的方法2,因爲quaternions已經在Irrlicht中可用。以下是我想出了計算旋轉:
#include <Rcpp.h>
#include <irrlicht.h>
#include <math.h>
using namespace Rcpp;
core::vector3df rotation_calc(DataFrame rcdf) {
NumericVector x = rcdf["x"];
NumericVector y = rcdf["y"];
NumericVector z = rcdf["z"];
// Z-axis
core::vector3df zaxis(0, 0, 1);
// resulting image's normal
core::vector3df normal = normal_calc(rcdf);
// calculate the rotation from the original image's normal (i.e. the Z-axis)
// to the resulting image's normal => quaternion P.
core::quaternion p;
p.rotationFromTo(zaxis, normal);
// take the midpoint of AB from the diagram in method 1, and rotate it with
// the quaternion P => vector U.
core::vector3df MAB(0, 0.5, 0);
core::quaternion m(MAB.X, MAB.Y, MAB.Z, 0);
core::quaternion rot = p * m * p.makeInverse();
core::vector3df u(rot.X, rot.Y, rot.Z);
// calculate the rotation from U to the midpoint of DE => quaternion Q
core::vector3df MDE(
(x(0) + x(1))/2,
(y(0) + y(1))/2,
(z(0) + z(1))/2
);
core::quaternion q;
q.rotationFromTo(u, MDE);
// multiply in the order Q * P, and convert to Euler angles
core::quaternion f = q * p;
core::vector3df euler;
f.toEuler(euler);
// to degrees
core::vector3df degrees(
euler.X * (180.0/M_PI),
euler.Y * (180.0/M_PI),
euler.Z * (180.0/M_PI)
);
Rcout << "degrees: " << degrees.X << ", " << degrees.Y << ", " << degrees.Z << std::endl;
return degrees;
}
結果是幾乎正確的,但有一個軸的旋轉是錯誤的。有沒有辦法解決這個問題,或者是我的實現固有缺陷?
這就是現在的結果。分數標記預期的角點。
什麼是'rcdf'? – meowgoesthedog
我正在使用[Rcpp](https://cran.r-project.org/web/packages/Rcpp/index.html)框架。它是一個DataFrame對象,表示 - 在這種情況下 - 一個包含3列和4行的表格。四個角點的x,y和z座標。對不起 - 我忘了描述這一點。 – nevrome
這個問題是隻有*兩個*球面座標角度;你需要三分之一來指定圖像在「普通」周圍的旋轉 - 這叫做滾動。你是否至少能夠讓圖像*平面指向正確的方向? – meowgoesthedog