첨부 실행 코드는 나눔고딕코딩 폰트를 사용합니다.
유용한 소스 코드가 있으면 icodebroker@naver.com으로 보내주시면 감사합니다.
블로그 자료는 자유롭게 사용하세요.

■ 고도 맵(Altitude Map)을 사용해 3차원 표면 그리기

------------------------------------------------------------------------------------------------------------------------


TestProject.zip


WriteableBitmapHelper.cs

 

 

using System.Windows;

using System.Windows.Media;

using System.Windows.Media.Imaging;

 

namespace TestProject

{

    /// <summary>

    /// 쓰기 가능 비트맵 헬퍼

    /// </summary>

    public class WriteableBitmapHelper

    {

        //////////////////////////////////////////////////////////////////////////////////////////////////// Field

        ////////////////////////////////////////////////////////////////////////////////////////// Private

 

        #region Field

 

        /// <summary>

        /// 너비

        /// </summary>

        private int width;

        

        /// <summary>

        /// 높이

        /// </summary>

        private int height;

 

        /// <summary>

        /// 픽셀 배열

        /// </summary>

        private byte[] pixelArray;

 

        /// <summary>

        /// 스트라이드

        /// </summary>

        private int stride;

 

        #endregion

 

        //////////////////////////////////////////////////////////////////////////////////////////////////// Constructor

        ////////////////////////////////////////////////////////////////////////////////////////// Public

 

        #region 생성자 - WriteableBitmapHelper(width, height)

 

        /// <summary>

        /// 생성자

        /// </summary>

        /// <param name="width">너비</param>

        /// <param name="height">높이</param>

        public WriteableBitmapHelper(int width, int height)

        {

            this.width  = width;

            this.height = height;

 

            this.pixelArray = new byte[width * height * 4];

 

            this.stride = width * 4;

        }

 

        #endregion

 

        //////////////////////////////////////////////////////////////////////////////////////////////////// Method

        ////////////////////////////////////////////////////////////////////////////////////////// Public

 

        #region 픽셀 구하기 - GetPixel(x, y, red, green, blue, alpha)

 

        /// <summary>

        /// 픽셀 구하기

        /// </summary>

        /// <param name="x">X 좌표</param>

        /// <param name="y">Y 좌표</param>

        /// <param name="red">빨강색</param>

        /// <param name="green">녹색</param>

        /// <param name="blue">파랑색</param>

        /// <param name="alpha">투명도</param>

        public void GetPixel(int x, int y, out byte red, out byte green, out byte blue, out byte alpha)

        {

            int index = y * this.stride + x * 4;

 

            blue  = this.pixelArray[index++];

            green = this.pixelArray[index++];

            red   = this.pixelArray[index++];

            alpha = this.pixelArray[index  ];

        }

 

        #endregion

        #region 파랑색 구하기 - GetBlue(x, y)

 

        /// <summary>

        /// 파랑색 구하기

        /// </summary>

        /// <param name="x">X 좌표</param>

        /// <param name="y">Y 좌표</param>

        /// <returns>파랑색</returns>

        public byte GetBlue(int x, int y)

        {

            return this.pixelArray[y * this.stride + x * 4];

        }

 

        #endregion

        #region 녹색 구하기 - GetGreen(x, y)

 

        /// <summary>

        /// 녹색 구하기

        /// </summary>

        /// <param name="x">X 좌표</param>

        /// <param name="y">Y 좌표</param>

        /// <returns>녹색</returns>

        public byte GetGreen(int x, int y)

        {

            return this.pixelArray[y * this.stride + x * 4 + 1];

        }

 

        #endregion

        #region 빨강색 구하기 - GetRed(x, y)

 

        /// <summary>

        /// 빨강색 구하기

        /// </summary>

        /// <param name="x">X 좌표</param>

        /// <param name="y">Y 좌표</param>

        /// <returns>빨강색</returns>

        public byte GetRed(int x, int y)

        {

            return this.pixelArray[y * this.stride + x * 4 + 2];

        }

 

        #endregion

        #region 투명도 구하기 - GetAlpha(x, y)

 

        /// <summary>

        /// 투명도 구하기

        /// </summary>

        /// <param name="x">X 좌표</param>

        /// <param name="y">Y 좌표</param>

        /// <returns>투명도</returns>

        public byte GetAlpha(int x, int y)

        {

            return this.pixelArray[y * this.stride + x * 4 + 3];

        }

 

        #endregion

        #region 픽셀 설정하기 - SetPixel(x, y, red, green, blue, alpha)

 

        /// <summary>

        /// 픽셀 설정하기

        /// </summary>

        /// <param name="x">X 좌표</param>

        /// <param name="y">Y 좌표</param>

        /// <param name="red">빨강색</param>

        /// <param name="green">녹색</param>

        /// <param name="blue">파랑색</param>

        /// <param name="alpha">투명도</param>

        public void SetPixel(int x, int y, byte red, byte green, byte blue, byte alpha)

        {

            int index = y * this.stride + x * 4;

 

            this.pixelArray[index++] = blue;

            this.pixelArray[index++] = green;

            this.pixelArray[index++] = red;

            this.pixelArray[index++] = alpha;

        }

 

        #endregion

        #region 파랑색 설정하기 - SetBlue(x, y, blue)

 

        /// <summary>

        /// 파랑색 설정하기

        /// </summary>

        /// <param name="x">X 좌표</param>

        /// <param name="y">Y 좌표</param>

        /// <param name="blue">파랑색</param>

        public void SetBlue(int x, int y, byte blue)

        {

            this.pixelArray[y * this.stride + x * 4] = blue;

        }

 

        #endregion

        #region 녹색 설정하기 - SetGreen(x, y, green)

 

        /// <summary>

        /// 녹색 설정하기

        /// </summary>

        /// <param name="x">X 좌표</param>

        /// <param name="y">Y 좌표</param>

        /// <param name="green">녹색</param>

        public void SetGreen(int x, int y, byte green)

        {

            this.pixelArray[y * this.stride + x * 4 + 1] = green;

        }

 

        #endregion

        #region 빨강색 설정하기 - SetRed(x, y, red)

 

        /// <summary>

        /// 빨강색 설정하기

        /// </summary>

        /// <param name="x">X 좌표</param>

        /// <param name="y">Y 좌표</param>

        /// <param name="red">빨강색</param>

        public void SetRed(int x, int y, byte red)

        {

            this.pixelArray[y * this.stride + x * 4 + 2] = red;

        }

 

        #endregion

        #region 투명도 설정하기 - SetAlpha(x, y, alpha)

 

        /// <summary>

        /// 투명도 설정하기

        /// </summary>

        /// <param name="x">X 좌표</param>

        /// <param name="y">Y 좌표</param>

        /// <param name="alpha">투명도</param>

        public void SetAlpha(int x, int y, byte alpha)

        {

            this.pixelArray[y * this.stride + x * 4 + 3] = alpha;

        }

 

        #endregion

        #region 색상 설정하기 - SetColor(red, green, blue)

 

        /// <summary>

        /// 색상 설정하기

        /// </summary>

        /// <param name="red">빨강색</param>

        /// <param name="green">녹색</param>

        /// <param name="blue">파랑색</param>

        public void SetColor(byte red, byte green, byte blue)

        {

            SetColor(red, green, blue, 255);

        }

 

        #endregion

        #region 색상 설정하기 - SetColor(red, green, blue, alpha)

 

        /// <summary>

        /// 색상 설정하기

        /// </summary>

        /// <param name="red">빨강색</param>

        /// <param name="green">녹색</param>

        /// <param name="blue">파랑색</param>

        /// <param name="alpha">투명도</param>

        public void SetColor(byte red, byte green, byte blue, byte alpha)

        {

            int byteCount = this.width * this.height * 4;

            int index     = 0;

 

            while(index < byteCount)

            {

                this.pixelArray[index++] = blue;

                this.pixelArray[index++] = green;

                this.pixelArray[index++] = red;

                this.pixelArray[index++] = alpha;

            }

        }

 

        #endregion

        #region 비트맵 구하기 - GetBitmap(dpiX, dpiY)

 

        /// <summary>

        /// 비트맵 구하기

        /// </summary>

        /// <param name="dpiX">X DPI</param>

        /// <param name="dpiY">Y DPI</param>

        /// <returns>쓰기 가능 비트맵</returns>

        public WriteableBitmap GetBitmap(double dpiX, double dpiY)

        {

            WriteableBitmap bitmap = new WriteableBitmap

            (

                this.width,

                this.height,

                dpiX,

                dpiY,

                PixelFormats.Bgra32,

                null

            );

 

            Int32Rect rectangle = new Int32Rect(0, 0, this.width, this.height);

 

            bitmap.WritePixels(rectangle, this.pixelArray, this.stride, 0);

 

            return bitmap;

        }

 

        #endregion

    }

}

 

 

WriteableBitmapExtention.cs

 

 

using System.IO;

using System.Windows.Media.Imaging;

 

namespace TestProject

{

    /// <summary>

    /// 쓰기 가능 비트맵 확장

    /// </summary>

    public static class WriteableBitmapExtention

    {

        //////////////////////////////////////////////////////////////////////////////////////////////////// Method

        ////////////////////////////////////////////////////////////////////////////////////////// Static

        //////////////////////////////////////////////////////////////////////////////// Public

 

        #region 저장하기 - Save(bitmap, filePath)

 

        /// <summary>

        /// 저장하기

        /// </summary>

        /// <param name="bitmap">비트맵</param>

        /// <param name="filePath">파일 경로</param>

        public static void Save(this WriteableBitmap bitmap, string filePath)

        {

            using(FileStream stream = new FileStream(filePath, FileMode.Create))

            {

                PngBitmapEncoder encoder = new PngBitmapEncoder();

 

                encoder.Frames.Add(BitmapFrame.Create(bitmap));

 

                encoder.Save(stream);

            }

        }

 

        #endregion

    }

}

 

 

MainWindow.xaml

 

 

<Window x:Class="TestProject.MainWindow"

    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"

    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"

    Width="800"

    Height="600"

    Title="고도 맵(Altitude Map)을 사용해 3차원 표면 그리기"

    Loaded="Window_Loaded"

    KeyDown="Window_KeyDown">

    <Grid>

        <Viewport3D Name="viewport3D" />

    </Grid>

</Window>

 

 

MainWindow.xaml.cs

 

 

using System;

using System.Collections.Generic;

using System.Linq;

using System.Windows;

using System.Windows.Input;

using System.Windows.Media;

using System.Windows.Media.Imaging;

using System.Windows.Media.Media3D;

 

namespace TestProject

{

    /// <summary>

    /// 메인 윈도우

    /// </summary>

    public partial class MainWindow : Window

    {

        //////////////////////////////////////////////////////////////////////////////////////////////////// Field

        ////////////////////////////////////////////////////////////////////////////////////////// Private

 

        #region Field

 

        /// <summary>

        /// 3차원 모델 그룹

        /// </summary>

        private Model3DGroup model3Dgroup = new Model3DGroup();

 

        /// <summary>

        /// 카메라

        /// </summary>

        private PerspectiveCamera camera;

 

        /// <summary>

        /// 카메라 파이

        /// </summary>

        private double cameraPhi = Math.PI / 6.0;

 

        /// <summary>

        /// 카메라 세타

        /// </summary>

        private double cameraTheta = Math.PI / 6.0;

 

        /// <summary>

        /// 카메라 R

        /// </summary>

        private double cameraR = 17.0;

 

        /// <summary>

        /// 카메라 델타 파이

        /// </summary>

        private const double CAMERA_DELTA_PHI = 0.1;

 

        /// <summary>

        /// 카메라 델타 세타

        /// </summary>

        private const double CAMERA_DELTA_THETA = 0.1;

 

        /// <summary>

        /// 카메라 델타 R

        /// </summary>

        private const double CAMERA_DELTA_R = 0.1;

 

        /// <summary>

        /// 최소값 X

        /// </summary>

        private int minimum_X;

 

        /// <summary>

        /// 최대값 X

        /// </summary>

        private int maximum_X;

 

        /// <summary>

        /// 델타 X

        /// </summary>

        private int deltaX;

 

        /// <summary>

        /// 최소값 Z

        /// </summary>

        private int minimumZ;

 

        /// <summary>

        /// 최대값 Z

        /// </summary>

        private int maximumZ;

 

        /// <summary>

        /// 델타 Z

        /// </summary>

        private int deltaZ;

 

        /// <summary>

        /// 텍스처 스케일 X

        /// </summary>

        private double textureScaleX;

 

        /// <summary>

        /// 텍스처 스케일 Z

        /// </summary>

        private double textureScaleZ;

 

        /// <summary>

        /// 3차원 포인트 딕셔너리

        /// </summary>

        private Dictionary<Point3D, int> point3DDictionary = new Dictionary<Point3D, int>();

 

        #endregion

 

        //////////////////////////////////////////////////////////////////////////////////////////////////// Constructor

        ////////////////////////////////////////////////////////////////////////////////////////// Public

 

        #region 생성자 - MainWindow()

 

        /// <summary>

        /// 생성자

        /// </summary>

        public MainWindow()

        {

            InitializeComponent();

        }

 

        #endregion

 

        //////////////////////////////////////////////////////////////////////////////////////////////////// Method

        ////////////////////////////////////////////////////////////////////////////////////////// Private

        //////////////////////////////////////////////////////////////////////////////// Event

 

        #region 윈도우 로드시 처리하기 - Window_Loaded(sender, e)

 

        /// <summary>

        /// 윈도우 로드시 처리하기

        /// </summary>

        /// <param name="sender">이벤트 발생자</param>

        /// <param name="e">이벤트 인자</param>

        private void Window_Loaded(object sender, RoutedEventArgs e)

        {

            this.camera = new PerspectiveCamera();

 

            this.camera.FieldOfView = 60;

 

            this.viewport3D.Camera = this.camera;

 

            SetCameraPosition();

 

            DefineLight();

 

            double[,] valueArray = GetValueArray();

 

            CreateAltitudeMap(valueArray);

 

            DefineModel(this.model3Dgroup, valueArray);

 

            ModelVisual3D modelVisual3D = new ModelVisual3D();

 

            modelVisual3D.Content = this.model3Dgroup;

 

            this.viewport3D.Children.Add(modelVisual3D);

        }

 

        #endregion

        #region 윈도우 키 DOWN 처리하기 - Window_KeyDown(sender, e)

 

        /// <summary>

        /// 윈도우 키 DOWN 처리하기

        /// </summary>

        /// <param name="sender">이벤트 발생자</param>

        /// <param name="e">이벤트 인자</param>

        private void Window_KeyDown(object sender, KeyEventArgs e)

        {

            switch(e.Key)

            {

                case Key.Up :

 

                    this.cameraPhi += CAMERA_DELTA_PHI;

 

                    if(this.cameraPhi > Math.PI / 2.0)

                    {

                        this.cameraPhi = Math.PI / 2.0;

                    }

 

                    break;

 

                case Key.Down :

 

                    this.cameraPhi -= CAMERA_DELTA_PHI;

 

                    if(this.cameraPhi < -Math.PI / 2.0)

                    {

                        this.cameraPhi = -Math.PI / 2.0;

                    }

 

                    break;

 

                case Key.Left :

 

                    this.cameraTheta += CAMERA_DELTA_THETA;

 

                    break;

 

                case Key.Right :

 

                    this.cameraTheta -= CAMERA_DELTA_THETA;

 

                    break;

 

                case Key.Add     :

                case Key.OemPlus :

 

                    this.cameraR -= CAMERA_DELTA_R;

 

                    if(this.cameraR < CAMERA_DELTA_R)

                    {

                        this.cameraR = CAMERA_DELTA_R;

                    }

 

                    break;

 

                case Key.Subtract :

                case Key.OemMinus :

 

                    this.cameraR += CAMERA_DELTA_R;

 

                    break;

            }

 

            SetCameraPosition();

        }

 

        #endregion

 

        //////////////////////////////////////////////////////////////////////////////// Function

 

        #region 카메라 위치 설정하기 - SetCameraPosition()

 

        /// <summary>

        /// 카메라 위치 설정하기

        /// </summary>

        private void SetCameraPosition()

        {

            double y   = this.cameraR * Math.Sin(this.cameraPhi);

            double hyp = this.cameraR * Math.Cos(this.cameraPhi);

            double x   = hyp * Math.Cos(this.cameraTheta);

            double z   = hyp * Math.Sin(this.cameraTheta);

 

            this.camera.Position = new Point3D(x, y, z);

 

            this.camera.LookDirection = new Vector3D(-x, -y, -z);

 

            this.camera.UpDirection = new Vector3D(0, 1, 0);

        }

 

        #endregion

        #region 조명 정의하기 - DefineLight()

 

        /// <summary>

        /// 조명 정의하기

        /// </summary>

        private void DefineLight()

        {

            AmbientLight ambientLight = new AmbientLight(Colors.Gray);

 

            DirectionalLight directionalLight = new DirectionalLight(Colors.Gray, new Vector3D(-1.0, -3.0, -2.0));

 

            this.model3Dgroup.Children.Add(ambientLight);

            this.model3Dgroup.Children.Add(directionalLight);

        }

 

        #endregion

        #region 값 배열 구하기 - GetValueArray()

 

        /// <summary>

        /// 값 배열 구하기

        /// </summary>

        /// <returns>값 배열</returns>

        private double[,] GetValueArray()

        {

            double[,] valueArray =

            {

                { 0, 0, 0, 1, 2, 2, 1, 0, 0, 0 },

                { 0, 0, 2, 3, 3, 3, 3, 2, 0, 0 },

                { 0, 2, 3, 4, 4, 4, 4, 3, 2, 0 },

                { 2, 3, 4, 5, 5, 5, 5, 4, 3, 2 },

                { 3, 4, 5, 6, 7, 7, 6, 5, 4, 3 },

                { 3, 4, 5, 6, 7, 7, 6, 5, 4, 3 },

                { 2, 3, 4, 5, 5, 5, 5, 4, 3, 2 },

                { 0, 2, 3, 4, 4, 4, 4, 3, 2, 0 },

                { 0, 0, 2, 3, 3, 3, 3, 2, 0, 0 },

                { 0, 0, 0, 1, 2, 2, 1, 0, 0, 0 }

            };

 

            this.minimum_X = 0;

            this.maximum_X = valueArray.GetUpperBound(0);

            this.deltaX    = 1;

            this.minimumZ  = 0;

            this.maximumZ  = valueArray.GetUpperBound(1);

            this.deltaZ    = 1;

 

            this.textureScaleX = (this.maximum_X - this.minimum_X);

            this.textureScaleZ = (this.maximumZ  - this.minimumZ );

 

            return valueArray;

        }

 

        #endregion

        #region 무지개 색상 설정하기 - SetRainbowColor(value, minimumValue, maximumValue, red, green, blue)

 

        /// <summary>

        /// 무지개 색상 설정하기

        /// </summary>

        /// <param name="value"></param>

        /// <param name="minimumValue">최소값</param>

        /// <param name="maximumValue">최대값</param>

        /// <param name="red">빨강색</param>

        /// <param name="green">녹색</param>

        /// <param name="blue">파랑색</param>

        private void SetRainbowColor(double value, double minimumValue, double maximumValue, out byte red, out byte green, out byte blue)

        {

            int targetValue = (int)(1023 * (value - minimumValue) / (maximumValue - minimumValue));

 

            if(targetValue < 256)

            {

                red   = 255;

                green = (byte)targetValue;

                blue  = 0;

            }

            else if(targetValue < 512)

            {

                targetValue -= 256;

 

                red   = (byte)(255 - targetValue);

                green = 255;

                blue  = 0;

            }

            else if(targetValue < 768)

            {

                targetValue -= 512;

 

                red   = 0;

                green = 255;

                blue  = (byte)targetValue;

            }

            else

            {

                targetValue -= 768;

 

                red   = 0;

                green = (byte)(255 - targetValue);

                blue  = 255;

            }

        }

 

        #endregion

        #region 고도 맵 생성하기 - CreateAltitudeMap(valueArray)

 

        /// <summary>

        /// 고도 맵 생성하기

        /// </summary>

        /// <param name="valueArray">값 배열</param>

        private void CreateAltitudeMap(double[,] valueArray)

        {

            int widthX = valueArray.GetUpperBound(0) + 1;

            int widthZ = valueArray.GetUpperBound(1) + 1;

 

            double deltaX = (this.maximum_X - this.minimum_X) / widthX;

            double deltaZ = (this.maximumZ  - this.minimumZ ) / widthZ;

 

            var valueEnumerable = from double value in valueArray

                             select value;

 

            double minimumY = valueEnumerable.Min();

            double maximumY = valueEnumerable.Max();

 

            WriteableBitmapHelper writeableBitmapHelper = new WriteableBitmapHelper(widthX, widthZ);

 

            for(int x = 0; x < widthX; x++)

            {

                for(int z = 0; z < widthZ; z++)

                {

                    byte red;

                    byte green;

                    byte blue;

 

                    SetRainbowColor

                    (

                        valueArray[x, z],

                        minimumY,

                        maximumY,

                        out red,

                        out green,

                        out blue

                    );

 

                    writeableBitmapHelper.SetPixel(x, z, red, green, blue, 255);

                }

            }

 

            WriteableBitmap wbitmap = writeableBitmapHelper.GetBitmap(96, 96);

 

            wbitmap.Save("texture.png");

        }

 

        #endregion

        #region 포인트 추가하기 - AddPoint(point3DCollection, textureCollection, point)

 

        /// <summary>

        /// 포인트 추가하기

        /// </summary>

        /// <param name="point3DCollection">3차원 포인트 컬렉션</param>

        /// <param name="textureCollection">텍스처 컬렉션</param>

        /// <param name="point">포인트</param>

        /// <returns>포인트 인덱스</returns>

        private int AddPoint(Point3DCollection point3DCollection, PointCollection textureCollection, Point3D point)

        {

            if(this.point3DDictionary.ContainsKey(point))

            {

                return this.point3DDictionary[point];

            }

 

            point3DCollection.Add(point);

 

            this.point3DDictionary.Add(point, point3DCollection.Count - 1);

 

            textureCollection.Add

            (

                new Point

                (

                    (point.X - this.minimum_X) * this.textureScaleX,

                    (point.Z - this.minimumZ ) * this.textureScaleZ

                )

            );

 

            return point3DCollection.Count - 1;

        }

 

        #endregion

        #region 삼각형 추가하기 - AddTriangle(meshGeometry3D, point1, point2, point3)

 

        /// <summary>

        /// 삼각형 추가하기

        /// </summary>

        /// <param name="meshGeometry3D">3차원 메쉬 기하</param>

        /// <param name="point1">포인트 1</param>

        /// <param name="point2">포인트 2</param>

        /// <param name="point3">포인트 3</param>

        private void AddTriangle(MeshGeometry3D meshGeometry3D, Point3D point1, Point3D point2, Point3D point3)

        {

            int index1 = AddPoint(meshGeometry3D.Positions, meshGeometry3D.TextureCoordinates, point1);

            int index2 = AddPoint(meshGeometry3D.Positions, meshGeometry3D.TextureCoordinates, point2);

            int index3 = AddPoint(meshGeometry3D.Positions, meshGeometry3D.TextureCoordinates, point3);

 

            meshGeometry3D.TriangleIndices.Add(index1);

            meshGeometry3D.TriangleIndices.Add(index2);

            meshGeometry3D.TriangleIndices.Add(index3);

        }

 

        #endregion

        #region 모델 정의하기 - DefineModel(model3DGroup, valueArray)

 

        /// <summary>

        /// 모델 정의하기

        /// </summary>

        /// <param name="model3DGroup">3차원 모델 그룹</param>

        /// <param name="valueArray">값 배열</param>

        private void DefineModel(Model3DGroup model3DGroup, double[,] valueArray)

        {

            MeshGeometry3D meshGeometry3D = new MeshGeometry3D();


            float offsetX = this.maximum_X / 2f;

            float offsetZ = this.maximumZ  / 2f;

 

            for(int x = this.minimum_X; x <= this.maximum_X - this.deltaX; x += this.deltaX)

            {

                for(int z = this.minimumZ; z <= this.maximumZ - this.deltaZ; z += this.deltaX)

                {

                    Point3D p00 = new Point3D(x - offsetX, valueArray[x, z], z - offsetZ);

                    Point3D p10 = new Point3D(x - offsetX + this.deltaX, valueArray[x + this.deltaX, z], z - offsetZ);

                    Point3D p01 = new Point3D(x - offsetX, valueArray[x, z + this.deltaZ], z - offsetZ + this.deltaZ);

                    Point3D p11 = new Point3D(x - offsetX + this.deltaX, valueArray[x + this.deltaX, z + this.deltaZ],

                        z - offsetZ + this.deltaZ);

 

                    AddTriangle(meshGeometry3D, p00, p01, p11);

                    AddTriangle(meshGeometry3D, p00, p11, p10);

                }

            }

 

            ImageBrush textureBrush = new ImageBrush();

 

            textureBrush.ImageSource = new BitmapImage(new Uri("texture.png", UriKind.Relative));

 

            DiffuseMaterial surfaceMaterial = new DiffuseMaterial(textureBrush);

 

            GeometryModel3D surfaceModel = new GeometryModel3D(meshGeometry3D, surfaceMaterial);

 

            surfaceModel.BackMaterial = surfaceMaterial;

 

            model3DGroup.Children.Add(surfaceModel);

        }

 

        #endregion

    }

}

 

------------------------------------------------------------------------------------------------------------------------

Posted by 사용자 icodebroker

댓글을 달아 주세요