2012-12-02 4 views
1

wpf에서 텍스처를 올바르게 매핑하는 데 어려움을 겪고 있습니다. 우선 3d는 내 힘이 아니지만 아래에 출력 샘플 코드와 이미지가 있습니다. 다각형을 가져 와서 삼각 측량을 수행 한 다음 사각형 텍스처를 출력에 매핑하려고합니다. 내가 얻는 문제는 부드럽게 곡선을 따라갈 수 있도록 텍스처를 매핑 할 수 없다는 것입니다. 하나의 텍스처 맵은 3dtools.dll 라이브러리를 활용했으며 훌륭하게 작동했지만 텍스처 맵의 결과는 왼쪽에 출력되었습니다. 내가 원하는대로 기울이지 않는다. 결과 이미지는 텍스처 좌표를 수동으로 이미지에 매핑하려는 시도입니다. 나는 그것이 왜 그렇게 보이는지 이해하지만, 그것을 고치는 방법을 정말로 모르겠습니다.WPF 3d에서 텍스처 매핑

private void simpleButtonClick(object sender, RoutedEventArgs e) 
     { 
      ClearViewport(); 
      SetCamera(); 

      PathGeometry FlatPath; 

      Geometry Geo = Geometry.Parse("M 0,0 L 0,10 C 4,4 6,6 10,10 V 0 C 6,-4 4,-6 0,0"); 
      var GeoText = FormattedText.BuildGeometry(new Point(0, 0)); 

      FlatPath = 
       Geo.GetFlattenedPathGeometry(.01, 
              ToleranceType. 
               Absolute); 
      var vertices = new List<Vertex>(); 
      foreach (PathFigure Figure in FlatPath.Figures) 
      { 
       List<Point> PointList = DumpFigureToList(Figure); 
       vertices.AddRange(PointList.Select(p=>new Vertex((float)p.X,(float)p.Y))); 
      } 

      // Write out the data set we're actually going to triangulate 
      var angulator = new Triangulator(); 

      List<Triad> triangles = angulator.Triangulation(vertices, true); 

      var Bounds = FlatPath.Bounds; 

      var mesh = new MeshGeometry3D(); 
      var cube = new Model3DGroup(); 
      var Count = 0; 
      foreach (var Tri in triangles) 
      { 
       Tri.MakeCounterClockwise(vertices); 
       if (FlatPath.FillContains(new Point(Tri.circumcircleX, Tri.circumcircleY))) 
       { 
        var p0 = new Point3D(vertices[Tri.a].x, vertices[Tri.a].y, 0); 
        var p1 = new Point3D(vertices[Tri.b].x, vertices[Tri.b].y, 0); 
        var p2 = new Point3D(vertices[Tri.c].x, vertices[Tri.c].y, 0); 


        mesh.Positions.Add(p0); 
        mesh.Positions.Add(p1); 
        mesh.Positions.Add(p2); 
        mesh.TriangleIndices.Add(Count); 
        Count++; 
        mesh.TriangleIndices.Add(Count); 
        Count++; 
        mesh.TriangleIndices.Add(Count); 
        Count++; 
        Vector3D normal = CalculateNormal(p0, p1, p2); 
        mesh.Normals.Add(normal); 
        mesh.Normals.Add(normal); 
        mesh.Normals.Add(normal); 



        mesh.TextureCoordinates.Add(new Point((Bounds.Left - vertices[Tri.a].x)/Bounds.Width, vertices[Tri.a].y > 0 ? 1 : 0)); 
        mesh.TextureCoordinates.Add(new Point((Bounds.Left - vertices[Tri.b].x)/Bounds.Width, vertices[Tri.b].y > 0 ? 1 : 0)); 
        mesh.TextureCoordinates.Add(new Point((Bounds.Left - vertices[Tri.c].x)/Bounds.Width, vertices[Tri.c].y > 0 ? 1 : 0)); 

        if (wireframeCheckBox.IsChecked == true) 
        { 
         var wireframe = new ScreenSpaceLines3D(); 
         wireframe.Points.Add(p0); 
         wireframe.Points.Add(p1); 
         wireframe.Points.Add(p2); 
         wireframe.Points.Add(p0); 
         wireframe.Color = Colors.LightBlue; 
         wireframe.Thickness = 2; 

         this.mainViewport.Children.Add(wireframe); 
        } 
       } 
      } 


      //mesh.TextureCoordinates = _3DTools.MeshUtils.GeneratePlanarTextureCoordinates(mesh, new Vector3D(0, 0, 1)); 

      var myBrush = new ImageBrush(); 
      myBrush.ImageSource = 
       new BitmapImage(new Uri(@"curvedown.png", UriKind.Absolute)); 
      Material material = new DiffuseMaterial(myBrush); 
      var model = new GeometryModel3D(mesh, material); 
      var group = new Model3DGroup(); 
      group.Children.Add(model); 

      PointLight light = new PointLight(Colors.White, new Point3D(10,10,10)); 
      group.Children.Add(light); 


      var Model = new ModelVisual3D(); 
      Model.Content = group; 
      this.mainViewport.Children.Add(Model); 

     } 

다음은 와이어 프레임의 출력입니다. 나는 주석 처리 된 텍스처 좌표 코드를 사용하고 있습니다. 오른쪽에 수동 코드 (주석 처리되지 않음). Image of output

답변

4

삼각 측량을 사용하면 예상 한대로 커브되지 않습니다. 그런 종류의 커브를 이루려면 얇은 줄무늬를 수동으로 생성해야합니다. 각 +가 정점입니다 - -

 

    ++++++++ 
    |||||||| 
    |||||||| 
    ++++++++ 

같은 것을 대신 직선을 만드는, 반경에 따라 특정 오프셋에서 공통 지점에서 오는 다른 라인 (가상 원)을 따라 매핑. 의사 코드

:

 

    for each i from 0 to nStripes 
     let angle = start + (end-start) * i/nStripes 
     let p1 = Point where 
     X = innerRadius * cos(angle) 
     Y = innerRadius * sin(angle) 
     let p2 = Point where 
     X = outerRadius * cos(angle) 
     Y = outerRadius * sin(angle) 
     add vertex at p1 
     add vertex at p2 

다음 이후에 이전에 생성 된 가장자리 페어이므로 (0,1) + (2,3), (2,3) 쿼드 것 + 연결 (4,5-) 다른, 등등 ...

줄 수를 충분히 결정해야합니다. 삼각형 내의 텍스처 매핑은 항상 곡선이 아닌 선형 보간법에 의해 수행되므로 커브 또는 사다리꼴과 같은 것들이 마술처럼 보이기를 기대할 수는 없습니다.