您的位置:首页 > 其它

WPF 3D变形

2012-04-06 17:34 344 查看
开始学习WPF中的3D的时候,在官方网站上看到过一个Demo就是将一个teapot扭曲,其中主要的一个类是Twister,该类主要是完成一个扭曲的效果,但是这个例子只是将一个随机的数值作为扭曲的结果,通过转换来实现的,那么我们如何通过加入现实生活中的数值来是扭曲达到我们想要的效果呢?

  由于刚刚开始接触3d的东西,对很多3d的东西还不熟悉,所以我设计的解决方案是将3d转化为2d的,那么就比较熟悉了。

首先,通过Blend将3d文件.obj导入到xaml中,你会发现一个规律,在同一个水平面上的顶点他们的Y是相同的,同一个竖直方向上的所有顶点他们的X和Z是相同的,那么可以通过对顶点分组可以是3d转化为2d。在实际的项目中可以根据具体的情况对顶点进行不同的分组方式。在这里我使用point.X和point.Z为可以来对顶点进行分组。大家可以想象下这样是不是使得3d的图形转化为2d的图形了。如下图:



然后复杂的问题就变得简单化了,这样只要通过某些操作是某些顶点发生位置的变化就可以达到对应模型的变化了,值得注意的是现在在2d中的一个point可是对应3d中的一组point。然而,理想中通过这种方式是可以将复杂的3d问题转化为简单的2d问题,但是出现了一个新的问题。大家都知道在3d中组成Model的基本元是三角形,而将三角形显示出来还需要一个叫索引的东西。那么通过分组后我怎么知道那些顶点要发生那些偏移呢?于是这里需要创建一个新的结构或者类。在本文中我使用的是一个struct,定义如下:

struct VertexPosition
{
public Point3D Point { get; set; }

public int Index { get; set; }

}

为了和wpf自带的一些类保持一致同时要需要创建一个名为VertexPositionCollection的类,来作为VertexPosition的集合类,定义如下:

VertexPositionCollection : List<VertexPosition>
{
VertexPositionCollection(Point3DCollection pointsSrc)
{
for (int i = 0; i < pointsSrc.Count; ++i)
{
this.Add(new VertexPosition() { Index = i, Point = pointsSrc[i] });
}
}
}

通过这样,就可以知道某一类分组包括的顶点以及顶点的索引,最后通过对2d中顶点的变化来遍历所有的分组中顶点,从而达到对3d中顶点的变化,最后在将2d的顶点还原为3d的顶点,这样就完成了3d顶点的一次转换。具体如下:

var points3Ds = new SortedList<int, Point3D>();
for (int i = 0; i < lineCount; i++)
{
var line = lines[i].ToList();
for (int j = 0; j < line.Count; j++)
{
var points = line[j].ToList();
foreach (var point in points)
{
    xform.OffsetY = linePointsTransforms[i, j]*progress*magnify/MILIMETERTOMETER;
    points3Ds.Add(point.Index, xform.Transform(point.Point));
   }
 }
}
return new Point3DCollection(points3Ds.Values);

我也是开始学习wpf的3d部分,有很多的东西还是不懂的,如果有什么不正确或者好的方法请大侠们指出来,大家一起学习学习。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: