示例#1
0
 public bool FindIntersectionTree(Point3d vectorStart, Vector3d vector,
                                  ref IObject3d nearestObj, ref Point3d nearestIntersectionPoint,
                                  ref float nearestIntersectionPointDist)
 {
     return(BoundingBox.VoxelIntersection(vector, vectorStart) &&
            Root.FindIntersectionNode(BoundingBox, vectorStart, vector, ref nearestObj,
                                      ref nearestIntersectionPoint, ref nearestIntersectionPointDist));
 }
示例#2
0
        private bool ObjectInVoxel(IObject3d obj)
        {
            Point3d min_p = obj.GetMinBoundaryPoint();
            Point3d max_p = obj.GetMaxBoundaryPoint();

            return
                (!(max_p.X < XMin || max_p.Y < YMin || max_p.Z < ZMin ||
                   min_p.X > XMax || min_p.Y > YMax || min_p.Z > ZMax));
        }
示例#3
0
        private Color Recursively(Scene scene, Point3d vectorStart, Vector3d vector,
                                  float intensity, int recursionLevel)
        {
            IObject3d nearestObj = null;
            Point3d   nearestIntersectionPoint     = new Point3d();
            float     nearestIntersectionPointDist = float.MaxValue;

            if (scene.KDTree.FindIntersectionTree(vectorStart, vector,
                                                  ref nearestObj, ref nearestIntersectionPoint, ref nearestIntersectionPointDist))
            {
                return(CalcColor(scene, vectorStart, vector, nearestObj, nearestIntersectionPoint,
                                 nearestIntersectionPointDist, intensity, recursionLevel));
            }

            return(scene.BackgroundColor);
        }
示例#4
0
        private bool IsViewable(Point3d targetPoint, Point3d startingPoint, Scene scene)
        {
            var   ray        = new Vector3d(startingPoint, targetPoint);
            float targetDist = Utils.ModuleVector(ray);

            IObject3d nearestObj = null;
            var       nearestIntersectionPoint     = new Point3d();
            var       nearestIntersectionPointDist = float.MaxValue;

            if (scene.KDTree.FindIntersectionTree(startingPoint, ray, ref nearestObj,
                                                  ref nearestIntersectionPoint, ref nearestIntersectionPointDist))
            {
                return(targetDist < nearestIntersectionPointDist);
            }

            return(true);
        }
示例#5
0
 public void AddObject(IObject3d obj)
 {
     Objects.Add(obj);
 }
示例#6
0
        private Color CalcColor(Scene scene, Point3d vectorStart, Vector3d vector, IObject3d obj,
                                Point3d point, float dist, float intensity, int recursionLevel)
        {
            Material material = obj.GetMaterial;
            Vector3d norm     = obj.GetNormalVector(point);

            Color objColor       = obj.GetColor;
            Color ambientColor   = new Color();
            Color diffuseColor   = new Color();
            Color reflectedColor = new Color();
            Color specularColor  = new Color();

            float fogDensity = (scene.FogDestiny?.Invoke(dist)) ?? 0;

            Vector3d reflectedRay = new Vector3d();

            if (material.Ks != 0f || material.Kr != 0f)
            {
                reflectedRay = ReflectRay(vector, norm);
            }

            // Ambient
            if (material.Ka != 0)
            {
                ambientColor = Color.MixColors(scene.BackgroundColor, objColor);
            }

            // Diffuse
            if (material.Kd != 0)
            {
                diffuseColor = objColor;
                if (scene.LightSources.Count > 0)
                {
                    Color light_color = GetLightingColor(point, norm, scene);
                    diffuseColor = Color.MixColors(diffuseColor, light_color);
                }
            }

            // Specular
            if (material.Ks != 0)
            {
                specularColor = scene.BackgroundColor;
                if (scene.LightSources.Count > 0)
                {
                    specularColor = GetSpecularColor(point, reflectedRay, scene, material.P);
                }
            }

            // Reflect
            if (material.Kr != 0)
            {
                if (intensity > Consts.INTENSITY && recursionLevel < Consts.RESUCRIONLEVEL)
                {
                    reflectedColor = Recursively(scene, point, reflectedRay, intensity * material.Kr * (1 - fogDensity),
                                                 recursionLevel + 1);
                }
                else
                {
                    reflectedColor = scene.BackgroundColor;
                }
            }

            // Result
            Color resultColor = new Color(0, 0, 0);

            if (material.Ka != 0)
            {
                resultColor = Color.AddColors(resultColor, Color.MulColor(ambientColor, material.Ka));
            }

            if (material.Kd != 0)
            {
                resultColor = Color.AddColors(resultColor, Color.MulColor(diffuseColor, material.Kd));
            }

            if (material.Ks != 0)
            {
                resultColor = Color.AddColors(resultColor, Color.MulColor(specularColor, material.Ks));
            }

            if (material.Kr != 0)
            {
                resultColor = Color.AddColors(resultColor, Color.MulColor(reflectedColor, material.Kr));
            }

            if (scene.FogDestiny != null)
            {
                resultColor = Color.AddColors(Color.MulColor(scene.BackgroundColor, fogDensity),
                                              Color.MulColor(resultColor, 1 - fogDensity));
            }

            return(resultColor);
        }
示例#7
0
        public bool FindIntersectionNode(Voxel v, Point3d vectorStart, Vector3d vector,
                                         ref IObject3d nearestObj, ref Point3d nearestIntersectionPoint,
                                         ref float nearestInersectionPointDist)
        {
            if (Plane == Plane.NONE)
            {
                if (Objects.Count > 0)
                {
                    Point3d intersectionPoint = new Point3d();

                    float     sqrNearestDist = float.MaxValue;
                    IObject3d tmpNearestObj  = null;
                    Point3d   tmpNearestIntersectionPoint = new Point3d();
                    float     sqrCurrDist;
                    bool      intersected = false;

                    for (var i = 0; i < Objects.Count; i++)
                    {
                        var obj = Objects[i];
                        if (obj.Intersect(vectorStart, vector, ref intersectionPoint) &&
                            v.PointInVoxel(intersectionPoint))
                        {
                            sqrCurrDist = Utils.SqrModuleVector(new Vector3d(vectorStart, intersectionPoint));

                            if (sqrCurrDist < sqrNearestDist || !intersected)
                            {
                                tmpNearestObj = obj;
                                tmpNearestIntersectionPoint = intersectionPoint;
                                sqrNearestDist = sqrCurrDist;
                                intersected    = true;
                            }
                        }
                    }

                    if (intersected)
                    {
                        float nearestDist = (float)Math.Sqrt(sqrNearestDist);

                        if (nearestDist < nearestInersectionPointDist)
                        {
                            nearestInersectionPointDist = nearestDist;
                            nearestObj = tmpNearestObj;
                            nearestIntersectionPoint = tmpNearestIntersectionPoint;
                        }
                    }
                    return(intersected);
                }
                return(false);
            }

            Voxel frontVoxel = new Voxel();
            Voxel backVoxel  = new Voxel();

            KDNode frontNode = null;
            KDNode backNode  = null;

            switch (Plane)
            {
            case Plane.XY:
                if ((Coord.Z > v.ZMin && Coord.Z > vectorStart.Z) ||
                    (Coord.Z < v.ZMin && Coord.Z < vectorStart.Z))
                {
                    InPlane(v, ref frontNode, ref backNode, ref frontVoxel, ref backVoxel);
                }
                else
                {
                    OutPlane(v, ref frontNode, ref backNode, ref frontVoxel, ref backVoxel);
                }
                break;

            case Plane.XZ:
                if ((Coord.Y > v.YMin && Coord.Y > vectorStart.Y) ||
                    (Coord.Y < v.YMin && Coord.Y < vectorStart.Y))
                {
                    InPlane(v, ref frontNode, ref backNode, ref frontVoxel, ref backVoxel);
                }
                else
                {
                    OutPlane(v, ref frontNode, ref backNode, ref frontVoxel, ref backVoxel);
                }
                break;

            case Plane.YZ:
                if ((Coord.X > v.XMin && Coord.X > vectorStart.X) ||
                    (Coord.X < v.XMin && Coord.X < vectorStart.X))
                {
                    InPlane(v, ref frontNode, ref backNode, ref frontVoxel, ref backVoxel);
                }
                else
                {
                    OutPlane(v, ref frontNode, ref backNode, ref frontVoxel, ref backVoxel);
                }
                break;

            case Plane.NONE:
                throw new Exception("[vector_plane_intersection] Plane is NONE. Error");
            }

            if (frontVoxel.VoxelIntersection(vector, vectorStart) &&
                frontNode.FindIntersectionNode(frontVoxel, vectorStart, vector,
                                               ref nearestObj, ref nearestIntersectionPoint, ref nearestInersectionPointDist))
            {
                return(true);
            }

            return(backVoxel.VoxelIntersection(vector, vectorStart) &&
                   backNode.FindIntersectionNode(backVoxel, vectorStart, vector,
                                                 ref nearestObj, ref nearestIntersectionPoint, ref nearestInersectionPointDist));
        }