三维视图控制
CSharpGL封装了多种控制器以操纵三维视图WinGLCanvas,包括第一人称视角(FirstPerspectiveManipulater)、卫星视角(SatelliteManipulater)、旋转控制器(ArcBallManipulater)和平移控制器(TranslateManipulater),第一人称和卫星视角常用于游戏,旋转和平移控制器常用于三维处理软件,比如CloudCompare、MeshLab等。
旋转
旋转控制器可以观察三维模型各个角度的局部特征,由于未改变模型的大小,所以被称作刚体变换。CSharpGL的原作者在这里详细阐述了ArcBall轨迹球的工作原理,大致是:将三维模型放在一个球中,将鼠标的水平移动轨迹转化为球上的弧段,再通过弧段计算出旋转轴和旋转角。CSharpGL可以直接用ArcBallManipulater类创建一个轨迹球,构造函数的参数为注册的鼠标按键:
ArcBallManipulater ball = new ArcBallManipulater(GLMouseButtons.Left);
为了让轨迹球适应到任意位置的相机上,需要将轨迹球和相机绑定到一起:
ball.Bind(scene.Camera, this.winGLCanvas1);
为了实时更新三维模型的旋转状态,还需要注册ArcBallManipulater 的Rotated事件:
ball.Rotated += manipulater_Rotated;
void manipulater_Rotated(object sender, CSharpGL.ArcBallManipulater.Rotation e)
{
SceneNodeBase node = scene.RootNode;
node.RotationAngle = e.angleInDegree;
node.RotationAxis = e.axis;
}
旋转控制器的解绑直接调用Unbind方法:
ball.Unbind();
平移
平移控制器也属于刚体变换,主要作用是观察三维模型在同一个裁剪面内不同位置的特征。和旋转控制器类似,平移控制器也可以通过简单的构造方法进行创建,两个参数分别是模型结点和注册的鼠标按键:
TranslateManipulater tran = new TranslateManipulater(scene.RootNode, GLMouseButtons.Right);
平移控制器同样需要绑定到相机上:
tran.Bind(scene.Camera, this.winGLCanvas1);
平移控制器的解绑也很简单
tran.Unbind();
缩放
三维模型的缩放是为了观察模型的细节和全貌,虽然CSharpGL未提供相关控制器,但是相机类(Camera)内包含的MouseWheel方法可用于缩放。操作方法如下:首先注册WinGLCanvas的MouseWheel事件:
winGLCanvas1.MouseWheel += openGLControl1_MouseWheel;
然后实现openGLControl1_MouseWheel方法:
private void openGLControl1_MouseWheel(object sender, MouseEventArgs e)
{
var scene = this.scene;
if (scene != null)
{
scene.Camera.MouseWheel(e.Delta);
}
}
缩放的解绑即取消openGLControl1_MouseWheel的注册:
winGLCanvas1.MouseWheel -= openGLControl1_MouseWheel;