using Earthblend.Tts.Common.Core.MeshGenerators.Base;
using Earthblend.Tts.Common.Core.Extentions;
using System;
using System.Collections.Generic;
using System.Windows;
using System.Windows.Input;
using System.Windows.Markup;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Media.Media3D;
using System.Xml.Serialization;
using Earthblend.Tts.Common.Core.Services;
using Earthblend.Tts.Common.Core.Enumerations;
using Earthblend.Tts.Common.Core.Members;
using Earthblend.Tts.Common.Core.CustomEventArgs;
using Earthblend.Nts.Common.MeshGenerators.Base;
using VirtualCanvasTestCode.Enumerations;
using Earthblend.DynamicCompile;

namespace Earthblend.Tts.Common.Core.MeshGenerators
{
    public class TorusMeshGenerator : MeshGeneratorBase
    {
        private ICommand _decreaseSpringRiseCommandIc; [XmlIgnore] public ICommand DecreaseSpringRiseCommandIc => _decreaseSpringRiseCommandIc ?? (_decreaseSpringRiseCommandIc = new RelayCommand<Object>(DecreaseSpringRiseCommandIcExecuted));
        private ICommand _increaseSpringRiseCommandIc; [XmlIgnore] public ICommand IncreaseSpringRiseCommandIc => _increaseSpringRiseCommandIc ?? (_increaseSpringRiseCommandIc = new RelayCommand<Object>(IncreaseSpringRiseCommandIcExecuted));


        private ICommand _decreaseRadiusCommandIc; [XmlIgnore] public ICommand DecreaseRadiusCommandIc => _decreaseRadiusCommandIc ?? (_decreaseRadiusCommandIc = new RelayCommand<Object>(DecreaseRadiusCommandIcExecuted));
        private ICommand _increaseRadiusCommandIc; [XmlIgnore] public ICommand IncreaseRadiusCommandIc => _increaseRadiusCommandIc ?? (_increaseRadiusCommandIc = new RelayCommand<Object>(IncreaseRadiusCommandIcExecuted));
        private ICommand _decreaseTubeRadiusCommandIc; [XmlIgnore] public ICommand DecreaseTubeRadiusCommandIc => _decreaseTubeRadiusCommandIc ?? (_decreaseTubeRadiusCommandIc = new RelayCommand<Object>(DecreaseTubeRadiusCommandIcExecuted));
        private ICommand _increaseTubeRadiusCommandIc; [XmlIgnore] public ICommand IncreaseTubeRadiusCommandIc => _increaseTubeRadiusCommandIc ?? (_increaseTubeRadiusCommandIc = new RelayCommand<Object>(IncreaseTubeRadiusCommandIcExecuted));
        private ICommand _decreaseStacksCommandIc; [XmlIgnore] public ICommand DecreaseStacksCommandIc => _decreaseStacksCommandIc ?? (_decreaseStacksCommandIc = new RelayCommand<Object>(DecreaseStacksCommandIcExecuted));
        private ICommand _increaseStacksCommandIc; [XmlIgnore] public ICommand IncreaseStacksCommandIc => _increaseStacksCommandIc ?? (_increaseStacksCommandIc = new RelayCommand<Object>(IncreaseStacksCommandIcExecuted));
        private ICommand _decreaseSlicesCommandIc; [XmlIgnore] public ICommand DecreaseSlicesCommandIc => _decreaseSlicesCommandIc ?? (_decreaseSlicesCommandIc = new RelayCommand<Object>(DecreaseSlicesCommandIcExecuted));
        private ICommand _increaseSlicesCommandIc; [XmlIgnore] public ICommand IncreaseSlicesCommandIc => _increaseSlicesCommandIc ?? (_increaseSlicesCommandIc = new RelayCommand<Object>(IncreaseSlicesCommandIcExecuted));

        private ICommand _decreaseStartSliceCommandIc; [XmlIgnore] public ICommand DecreaseStartSliceCommandIc => _decreaseStartSliceCommandIc ?? (_decreaseStartSliceCommandIc = new RelayCommand<Object>(DecreaseStartSliceCommandIcExecuted));
        private ICommand _increaseStartSliceCommandIc; [XmlIgnore] public ICommand IncreaseStartSliceCommandIc => _increaseStartSliceCommandIc ?? (_increaseStartSliceCommandIc = new RelayCommand<Object>(IncreaseStartSliceCommandIcExecuted));
        private ICommand _decreaseEndSliceCommandIc; [XmlIgnore] public ICommand DecreaseEndSliceCommandIc => _decreaseEndSliceCommandIc ?? (_decreaseEndSliceCommandIc = new RelayCommand<Object>(DecreaseEndSliceCommandIcExecuted));
        private ICommand _increaseEndSliceCommandIc; [XmlIgnore] public ICommand IncreaseEndSliceCommandIc => _increaseEndSliceCommandIc ?? (_increaseEndSliceCommandIc = new RelayCommand<Object>(IncreaseEndSliceCommandIcExecuted));

        private ICommand _decreaseThetaStartCommandIc; [XmlIgnore] public ICommand DecreaseThetaStartCommandIc => _decreaseThetaStartCommandIc ?? (_decreaseThetaStartCommandIc = new RelayCommand<Object>(DecreaseThetaStartCommandIcExecuted));
        private ICommand _increaseThetaStartCommandIc; [XmlIgnore] public ICommand IncreaseThetaStartCommandIc => _increaseThetaStartCommandIc ?? (_increaseThetaStartCommandIc = new RelayCommand<Object>(IncreaseThetaStartCommandIcExecuted));
        private ICommand _decreaseThetaStopCommandIc; [XmlIgnore] public ICommand DecreaseThetaStopCommandIc => _decreaseThetaStopCommandIc ?? (_decreaseThetaStopCommandIc = new RelayCommand<Object>(DecreaseThetaStopCommandIcExecuted));
        private ICommand _increaseThetaStopCommandIc; [XmlIgnore] public ICommand IncreaseThetaStopCommandIc => _increaseThetaStopCommandIc ?? (_increaseThetaStopCommandIc = new RelayCommand<Object>(IncreaseThetaStopCommandIcExecuted));

        public void DecreaseSpringRiseCommandIcExecuted(Object sender) { SpringRise -= MovementValue; }
        public void IncreaseSpringRiseCommandIcExecuted(Object sender) { SpringRise += MovementValue; }

        public void DecreaseRadiusCommandIcExecuted(Object sender) { Radius -= MovementValue; }
        public void IncreaseRadiusCommandIcExecuted(Object sender) { Radius += MovementValue; }
        public void DecreaseTubeRadiusCommandIcExecuted(Object sender) { TubeRadius -= MovementValue; }
        public void IncreaseTubeRadiusCommandIcExecuted(Object sender) { TubeRadius += MovementValue; }
        public void DecreaseStacksCommandIcExecuted(Object sender) { Stacks--; }
        public void IncreaseStacksCommandIcExecuted(Object sender) { Stacks++; }
        public void DecreaseSlicesCommandIcExecuted(Object sender) { Slices--; }
        public void IncreaseSlicesCommandIcExecuted(Object sender) { Slices++; }

        public void DecreaseStartSliceCommandIcExecuted(Object sender) { StartSlice--; }
        public void IncreaseStartSliceCommandIcExecuted(Object sender) { StartSlice++; }
        public void DecreaseEndSliceCommandIcExecuted(Object sender) { EndSlice--; }
        public void IncreaseEndSliceCommandIcExecuted(Object sender) { EndSlice++; }

        public void DecreaseThetaStartCommandIcExecuted(Object sender) { ThetaStart--; }
        public void IncreaseThetaStartCommandIcExecuted(Object sender) { ThetaStart++; }
        public void DecreaseThetaStopCommandIcExecuted(Object sender) { ThetaStop--; }
        public void IncreaseThetaStopCommandIcExecuted(Object sender) { ThetaStop++; }

        public TorusMeshGenerator Duplicate()
        {
            TorusMeshGenerator meshGenerator = new TorusMeshGenerator();

            meshGenerator.Radius = Radius;
            meshGenerator.TubeRadius = TubeRadius;
            meshGenerator.Slices = Slices;
            meshGenerator.StartSlice = StartSlice;
            meshGenerator.EndSlice = EndSlice;
            meshGenerator.ThetaStart = ThetaStart;
            meshGenerator.ThetaStop = ThetaStop;
            meshGenerator.Stacks = Stacks;
            meshGenerator.SpringRise = SpringRise;
            meshGenerator.Axis = Axis;

            return meshGenerator;
        }

        public TorusMeshGenerator() { PropertyChanged(new DependencyPropertyChangedEventArgs()); }
        public static IList<String> Properties = new List<String>() { "Radius", "TubeRadius", "Slices", "Stacks" };


        public static readonly DependencyProperty RenderStyleProperty = DependencyProperty.Register("RenderStyle", typeof(ThetaStopRenderStyle), typeof(TorusMeshGenerator), new PropertyMetadata(ThetaStopRenderStyle.Default, PropertyChanged));

        public static readonly DependencyProperty SpringRiseProperty = DependencyProperty.Register("SpringRise", typeof(double), typeof(TorusMeshGenerator), new PropertyMetadata(0D, PropertyChanged));

        public static readonly DependencyProperty RadiusProperty = DependencyProperty.Register("Radius", typeof(double), typeof(TorusMeshGenerator), new PropertyMetadata(1.0, PropertyChanged));
        public static readonly DependencyProperty TubeRadiusProperty = DependencyProperty.Register("TubeRadius", typeof(double), typeof(TorusMeshGenerator), new PropertyMetadata(0.25, PropertyChanged));
        public static readonly DependencyProperty SlicesProperty = DependencyProperty.Register("Slices", typeof(int), typeof(TorusMeshGenerator), new PropertyMetadata(36, PropertyChanged), ValidateSlices);
        public static readonly DependencyProperty StacksProperty = DependencyProperty.Register("Stacks", typeof(int), typeof(TorusMeshGenerator), new PropertyMetadata(36, PropertyChanged), ValidateStacks);
        public static readonly DependencyProperty StartSliceProperty = DependencyProperty.Register("StartSlice", typeof(int), typeof(TorusMeshGenerator), new PropertyMetadata(1, PropertyChanged), ValidateStartSlices);
        public static readonly DependencyProperty EndSliceProperty = DependencyProperty.Register("EndSlice", typeof(int), typeof(TorusMeshGenerator), new PropertyMetadata(18, PropertyChanged), ValidateSlices);
        public static readonly DependencyProperty ThetaStartProperty = DependencyProperty.Register("ThetaStart", typeof(int), typeof(TorusMeshGenerator), new PropertyMetadata(0, PropertyChanged), ValidateThetaStart);
        public static readonly DependencyProperty ThetaStopProperty = DependencyProperty.Register("ThetaStop", typeof(int), typeof(TorusMeshGenerator), new PropertyMetadata(36, PropertyChanged), ValidateThetaStop);

        public ThetaStopRenderStyle RenderStyle { set { SetValue(RenderStyleProperty, value); } get { return (ThetaStopRenderStyle)GetValue(RenderStyleProperty); } }

        public double SpringRise { set { SetValue(SpringRiseProperty, value); } get { return (double)GetValue(SpringRiseProperty); } }

        public double Radius { set { SetValue(RadiusProperty, value); } get { return (double)GetValue(RadiusProperty); } }
        public double TubeRadius { set { SetValue(TubeRadiusProperty, value); } get { return (double)GetValue(TubeRadiusProperty); } }
        public int Slices { set { SetValue(SlicesProperty, value); } get { return (int)GetValue(SlicesProperty); } }
        public int Stacks { set { SetValue(StacksProperty, value); } get { return (int)GetValue(StacksProperty); } }
        public int StartSlice { set { SetValue(StartSliceProperty, value); } get { return (int)GetValue(StartSliceProperty); } }
        public int EndSlice { set { SetValue(EndSliceProperty, value); } get { return (int)GetValue(EndSliceProperty); } }

        public int ThetaStart { set { SetValue(ThetaStartProperty, value); } get { return (int)GetValue(ThetaStartProperty); } }
        public int ThetaStop { set { SetValue(ThetaStopProperty, value); } get { return (int)GetValue(ThetaStopProperty); } }


        static bool ValidateSlices(object obj) { return true; } //(int)obj > 2;
        static bool ValidateStartSlices(object obj) { return true; } // (int)obj >= 0; }
        static bool ValidateThetaStart(object obj) { return true; } //return (int)obj >= 0; }
        static bool ValidateStacks(object obj) { return true; } //(int)obj > 2;
        static bool ValidateThetaStop(object obj) { return true; } // (int)obj >= 1;
        protected override void Triangulate(DependencyPropertyChangedEventArgs args
            , Point3DCollection vertices,
              Vector3DCollection normals,
              Int32Collection indices
            , PointCollection textures
            )
        {
            vertices.Clear();
            normals.Clear();
            indices.Clear();
            textures.Clear();

            #region Torus Mesh Generator - Good Code

            CustomMeshBuilder meshBuilder = new CustomMeshBuilder();

            meshBuilder.AddTorus(Radius * 2, TubeRadius * 2, Slices, Stacks, ThetaStop, Axis);

            vertices = meshBuilder.Positions;
            normals = meshBuilder.Normals;
            indices = meshBuilder.TriangleIndices;
            textures = meshBuilder.TextureCoordinates;

            Geometry = new MeshGeometry3D() { Positions = vertices, Normals = normals, TriangleIndices = indices, TextureCoordinates = textures };

            meshBuilder = null;

            OnMeshChanged(new MeshEventArgs(Geometry as MeshGeometry3D));

            #endregion

            // Fill the vertices, normals, and textures collections.
            //for (int stack = ThetaStart; stack <= ThetaStop; stack++)
            //{
            //    double phi = stack * 2 * Math.PI / Stacks;

            //    double xCenter = Radius * Math.Sin(phi);
            //    double yCenter = Radius * Math.Cos(phi);
            //    Point3D pointCenter = new Point3D(xCenter, yCenter, 0);

            //    for (int slice = 0; slice <= Slices; slice++)
            //    {
            //        double theta = slice * 2 * Math.PI / Slices + Math.PI;
            //        double x = (Radius + TubeRadius * Math.Cos(theta)) * Math.Sin(phi);
            //        double y = (Radius + TubeRadius * Math.Cos(theta)) * Math.Cos(phi);
            //        double z = -TubeRadius * Math.Sin(theta);
            //        Point3D point = new Point3D(x, y, z);

            //        vertices.Add(point);
            //        normals.Add(point - pointCenter);
            //        textures.Add(new Point((double)slice / Slices, (double)stack / Stacks));
            //    }
            //}

            //// Fill the indices collection.
            //for (int stack = ThetaStart; stack < ThetaStop; stack++)
            //{
            //    for (int slice = 0; slice < Slices; slice++)
            //    {
            //        indices.Add((stack + 0) * (Slices + 1) + slice);
            //        indices.Add((stack + 1) * (Slices + 1) + slice);
            //        indices.Add((stack + 0) * (Slices + 1) + slice + 1);

            //        indices.Add((stack + 0) * (Slices + 1) + slice + 1);
            //        indices.Add((stack + 1) * (Slices + 1) + slice);
            //        indices.Add((stack + 1) * (Slices + 1) + slice + 1);
            //    }
            //}
        }
    }
}




//using Earthblend.DynamicCompile;
//using Earthblend.Nts.Common.MeshGenerators.Base;
//using Earthblend.Tts.Common.Core.MeshGenerators.Base;
//using Earthblend.Tts.Common.Core.Services;
//using System;
//using System.Collections.Generic;
//using System.Windows;
//using System.Windows.Input;
//using System.Windows.Markup;
//using System.Windows.Media;
//using System.Windows.Media.Animation;
//using System.Windows.Media.Media3D;
//using System.Xml.Serialization;
//using VirtualCanvasTestCode.Enumerations;
//using VirtualCanvasTestCode.Extensions;

//namespace Earthblend.Tts.Common.Core.MeshGenerators
//{
//    public class TorusMeshGenerator : MeshGeneratorBase
//    {
//        private ICommand _decreaseRadiusCommandIc; [XmlIgnore] public ICommand DecreaseRadiusCommandIc => _decreaseRadiusCommandIc ?? (_decreaseRadiusCommandIc = new RelayCommand<Object>(DecreaseRadiusCommandIcExecuted));
//        private ICommand _increaseRadiusCommandIc; [XmlIgnore] public ICommand IncreaseRadiusCommandIc => _increaseRadiusCommandIc ?? (_increaseRadiusCommandIc = new RelayCommand<Object>(IncreaseRadiusCommandIcExecuted));
//        private ICommand _decreaseTubeRadiusCommandIc;[XmlIgnore] public ICommand DecreaseTubeRadiusCommandIc => _decreaseTubeRadiusCommandIc ?? (_decreaseTubeRadiusCommandIc = new RelayCommand<Object>(DecreaseTubeRadiusCommandIcExecuted));
//        private ICommand _increaseTubeRadiusCommandIc;[XmlIgnore] public ICommand IncreaseTubeRadiusCommandIc => _increaseTubeRadiusCommandIc ?? (_increaseTubeRadiusCommandIc = new RelayCommand<Object>(IncreaseTubeRadiusCommandIcExecuted));
//        private ICommand _decreaseStacksCommandIc;[XmlIgnore] public ICommand DecreaseStacksCommandIc => _decreaseStacksCommandIc ?? (_decreaseStacksCommandIc = new RelayCommand<Object>(DecreaseStacksCommandIcExecuted));
//        private ICommand _increaseStacksCommandIc;[XmlIgnore] public ICommand IncreaseStacksCommandIc => _increaseStacksCommandIc ?? (_increaseStacksCommandIc = new RelayCommand<Object>(IncreaseStacksCommandIcExecuted));
//        private ICommand _decreaseSlicesCommandIc;[XmlIgnore] public ICommand DecreaseSlicesCommandIc => _decreaseSlicesCommandIc ?? (_decreaseSlicesCommandIc = new RelayCommand<Object>(DecreaseSlicesCommandIcExecuted));
//        private ICommand _increaseSlicesCommandIc;[XmlIgnore] public ICommand IncreaseSlicesCommandIc => _increaseSlicesCommandIc ?? (_increaseSlicesCommandIc = new RelayCommand<Object>(IncreaseSlicesCommandIcExecuted));

//        private ICommand _decreaseStartSliceCommandIc;[XmlIgnore] public ICommand DecreaseStartSliceCommandIc => _decreaseStartSliceCommandIc ?? (_decreaseStartSliceCommandIc = new RelayCommand<Object>(DecreaseStartSliceCommandIcExecuted));
//        private ICommand _increaseStartSliceCommandIc;[XmlIgnore] public ICommand IncreaseStartSliceCommandIc => _increaseStartSliceCommandIc ?? (_increaseStartSliceCommandIc = new RelayCommand<Object>(IncreaseStartSliceCommandIcExecuted));
//        private ICommand _decreaseEndSliceCommandIc;[XmlIgnore] public ICommand DecreaseEndSliceCommandIc => _decreaseEndSliceCommandIc ?? (_decreaseEndSliceCommandIc = new RelayCommand<Object>(DecreaseEndSliceCommandIcExecuted));
//        private ICommand _increaseEndSliceCommandIc;[XmlIgnore] public ICommand IncreaseEndSliceCommandIc => _increaseEndSliceCommandIc ?? (_increaseEndSliceCommandIc = new RelayCommand<Object>(IncreaseEndSliceCommandIcExecuted));

//        private ICommand _decreaseThetaStartCommandIc;[XmlIgnore] public ICommand DecreaseThetaStartCommandIc => _decreaseThetaStartCommandIc ?? (_decreaseThetaStartCommandIc = new RelayCommand<Object>(DecreaseThetaStartCommandIcExecuted));
//        private ICommand _increaseThetaStartCommandIc;[XmlIgnore] public ICommand IncreaseThetaStartCommandIc => _increaseThetaStartCommandIc ?? (_increaseThetaStartCommandIc = new RelayCommand<Object>(IncreaseThetaStartCommandIcExecuted));
//        private ICommand _decreaseThetaStopCommandIc;[XmlIgnore] public ICommand DecreaseThetaStopCommandIc => _decreaseThetaStopCommandIc ?? (_decreaseThetaStopCommandIc = new RelayCommand<Object>(DecreaseThetaStopCommandIcExecuted));
//        private ICommand _increaseThetaStopCommandIc;[XmlIgnore] public ICommand IncreaseThetaStopCommandIc => _increaseThetaStopCommandIc ?? (_increaseThetaStopCommandIc = new RelayCommand<Object>(IncreaseThetaStopCommandIcExecuted));


//        public void DecreaseRadiusCommandIcExecuted(Object sender) { Radius-=MovementValue; }
//        public void IncreaseRadiusCommandIcExecuted(Object sender) { Radius+=MovementValue; }
//        public void DecreaseTubeRadiusCommandIcExecuted(Object sender) { TubeRadius-=MovementValue; }
//        public void IncreaseTubeRadiusCommandIcExecuted(Object sender) { TubeRadius+=MovementValue; }
//        public void DecreaseStacksCommandIcExecuted(Object sender) { Stacks--; }
//        public void IncreaseStacksCommandIcExecuted(Object sender) { Stacks++; }
//        public void DecreaseSlicesCommandIcExecuted(Object sender) { Slices--; }
//        public void IncreaseSlicesCommandIcExecuted(Object sender) { Slices++; }

//        public void DecreaseStartSliceCommandIcExecuted(Object sender) { StartSlice--; }
//        public void IncreaseStartSliceCommandIcExecuted(Object sender) { StartSlice++; }
//        public void DecreaseEndSliceCommandIcExecuted(Object sender) { EndSlice--; }
//        public void IncreaseEndSliceCommandIcExecuted(Object sender) { EndSlice++; }

//        public void DecreaseThetaStartCommandIcExecuted(Object sender) { ThetaStart--; }
//        public void IncreaseThetaStartCommandIcExecuted(Object sender) { ThetaStart++; }
//        public void DecreaseThetaStopCommandIcExecuted(Object sender) { ThetaStop--; }
//        public void IncreaseThetaStopCommandIcExecuted(Object sender) { ThetaStop++; }

//        public TorusMeshGenerator Duplicate()
//        {
//            TorusMeshGenerator meshGenerator = new TorusMeshGenerator();

//            meshGenerator.Radius = Radius;
//            meshGenerator.TubeRadius = TubeRadius;
//            meshGenerator.Slices = Slices;
//            meshGenerator.StartSlice = StartSlice;
//            meshGenerator.EndSlice = EndSlice;
//            meshGenerator.ThetaStart = ThetaStart;
//            meshGenerator.ThetaStop = ThetaStop;
//            meshGenerator.Stacks = Stacks;

//            return meshGenerator;
//        }

//        public TorusMeshGenerator() { PropertyChanged(new DependencyPropertyChangedEventArgs()); }
//        public static IList<String> Properties = new List<String>() { "Radius", "TubeRadius", "Slices", "Stacks" };


//        public static readonly DependencyProperty RenderStyleProperty = DependencyProperty.Register("RenderStyle", typeof(ThetaStopRenderStyle), typeof(TorusMeshGenerator), new PropertyMetadata(ThetaStopRenderStyle.Default, PropertyChanged));

//        public static readonly DependencyProperty RadiusProperty = DependencyProperty.Register("Radius", typeof(double), typeof(TorusMeshGenerator), new PropertyMetadata(1.0, PropertyChanged));
//        public static readonly DependencyProperty TubeRadiusProperty = DependencyProperty.Register("TubeRadius", typeof(double), typeof(TorusMeshGenerator), new PropertyMetadata(0.25, PropertyChanged));
//        public static readonly DependencyProperty SlicesProperty = DependencyProperty.Register("Slices", typeof(int), typeof(TorusMeshGenerator), new PropertyMetadata(18, PropertyChanged), ValidateSlices);
//        public static readonly DependencyProperty StacksProperty = DependencyProperty.Register("Stacks", typeof(int), typeof(TorusMeshGenerator), new PropertyMetadata(36, PropertyChanged), ValidateStacks);
//        public static readonly DependencyProperty StartSliceProperty = DependencyProperty.Register("StartSlice", typeof(int), typeof(TorusMeshGenerator), new PropertyMetadata(1, PropertyChanged), ValidateStartSlices);
//        public static readonly DependencyProperty EndSliceProperty = DependencyProperty.Register("EndSlice", typeof(int), typeof(TorusMeshGenerator), new PropertyMetadata(18, PropertyChanged), ValidateSlices);
//        public static readonly DependencyProperty ThetaStartProperty = DependencyProperty.Register("ThetaStart", typeof(int), typeof(TorusMeshGenerator), new PropertyMetadata(0, PropertyChanged), ValidateThetaStart);
//        public static readonly DependencyProperty ThetaStopProperty = DependencyProperty.Register("ThetaStop", typeof(int), typeof(TorusMeshGenerator), new PropertyMetadata(36, PropertyChanged), ValidateThetaStop);

//        public ThetaStopRenderStyle RenderStyle { set { SetValue(RenderStyleProperty, value); } get { return (ThetaStopRenderStyle)GetValue(RenderStyleProperty); } }

//        public double Radius { set { SetValue(RadiusProperty, value); } get { return (double)GetValue(RadiusProperty); } }
//        public double TubeRadius { set { SetValue(TubeRadiusProperty, value); } get { return (double)GetValue(TubeRadiusProperty); } }
//        public int Slices { set { SetValue(SlicesProperty, value); } get { return (int)GetValue(SlicesProperty); } }
//        public int Stacks { set { SetValue(StacksProperty, value); } get { return (int)GetValue(StacksProperty); } }
//        public int StartSlice { set { SetValue(StartSliceProperty, value); } get { return (int)GetValue(StartSliceProperty); } }
//        public int EndSlice { set { SetValue(EndSliceProperty, value); } get { return (int)GetValue(EndSliceProperty); } }

//        public int ThetaStart { set { SetValue(ThetaStartProperty, value); } get { return (int)GetValue(ThetaStartProperty); } }
//        public int ThetaStop { set { SetValue(ThetaStopProperty, value); } get { return (int)GetValue(ThetaStopProperty); } }


//        static bool ValidateSlices(object obj) { return true; } //(int)obj > 2;
//        static bool ValidateStartSlices(object obj) { return true; } // (int)obj >= 0; }
//        static bool ValidateThetaStart(object obj) { return true; } //return (int)obj >= 0; }
//        static bool ValidateStacks(object obj) { return true; } //(int)obj > 2;
//        static bool ValidateThetaStop(object obj) { return true; } // (int)obj >= 1;
//        protected override void Triangulate(DependencyPropertyChangedEventArgs args
//            , Point3DCollection vertices,
//              Vector3DCollection normals,
//              Int32Collection indices
//            , PointCollection textures
//            )
//        {
//            vertices.Clear();
//            normals.Clear();
//            indices.Clear();
//            textures.Clear();

//            TorusMeshGeneratorService meshService = new TorusMeshGeneratorService()
//            {
//                 ThetaStart = ThetaStart
//                ,ThetaStop = ThetaStop
//                ,Radius = Radius
//                ,TubeRadius = TubeRadius
//                ,Stacks = Stacks
//                ,Slices = Slices
//            };

//            MeshGeometry3D mesh = null;

//            switch(RenderStyle)
//            {
//                case ThetaStopRenderStyle.Default:
//                    mesh = meshService.GenerateMesh();
//                    break;
//                case ThetaStopRenderStyle.Gap:
//                    mesh = meshService.GenerateMeshGap();
//                    break;
//            }

//            vertices.AddRange(mesh.Positions);
//            indices.AddRange(mesh.TriangleIndices);
//            textures.AddRange(mesh.TextureCoordinates);
//            normals.AddRange(mesh.Normals);

//            //meshService = null;

//            // Fill the vertices, normals, and textures collections.
//            //for (int stack = ThetaStart; stack <= ThetaStop; stack++)
//            //{
//            //    double phi = stack * 2 * Math.PI / Stacks;

//            //    double xCenter = Radius * Math.Sin(phi);
//            //    double yCenter = Radius * Math.Cos(phi);
//            //    Point3D pointCenter = new Point3D(xCenter, yCenter, 0);

//            //    for (int slice = 0; slice <= Slices; slice++)
//            //    {
//            //        double theta = slice * 2 * Math.PI / Slices + Math.PI;
//            //        double x = (Radius + TubeRadius * Math.Cos(theta)) * Math.Sin(phi);
//            //        double y = (Radius + TubeRadius * Math.Cos(theta)) * Math.Cos(phi);
//            //        double z = -TubeRadius * Math.Sin(theta);
//            //        Point3D point = new Point3D(x, y, z);

//            //        vertices.Add(point);
//            //        normals.Add(point - pointCenter);
//            //        textures.Add(new Point((double)slice / Slices, (double)stack / Stacks));
//            //    }
//            //}

//            //// Fill the indices collection.
//            //for (int stack = ThetaStart; stack < ThetaStop; stack++)
//            //{
//            //    for (int slice = 0; slice < Slices; slice++)
//            //    {
//            //        indices.Add((stack + 0) * (Slices + 1) + slice);
//            //        indices.Add((stack + 1) * (Slices + 1) + slice);
//            //        indices.Add((stack + 0) * (Slices + 1) + slice + 1);

//            //        indices.Add((stack + 0) * (Slices + 1) + slice + 1);
//            //        indices.Add((stack + 1) * (Slices + 1) + slice);
//            //        indices.Add((stack + 1) * (Slices + 1) + slice + 1);
//            //    }
//            //}
//        }
//    }
//}

