Пример #1
0
        protected override Real getValue(MovableObject movableObject, Camera camera)
        {
            // Get viewport
            var viewport = camera.Viewport;

            // Get viewport area
            float viewportArea = viewport.ActualWidth * viewport.ActualHeight;

            // Get area of unprojected circle with object bounding radius
            float boundingArea = MathHelper.PI * MathHelper.Sqr(movableObject.BoundingRadius);

            // Base computation on projection type
            switch (camera.ProjectionType)
            {
            case Projection.Perspective:
            {
                // Get camera distance
                var distanceSquared = movableObject.ParentNode.GetSquaredViewDepth(camera);

                // Check for 0 distance
                if (distanceSquared <= float.Epsilon)
                {
                    return(BaseValue);
                }

                // Get projection matrix (this is done to avoid computation of tan(fov / 2))
                var projectionMatrix = camera.ProjectionMatrix;

                //estimate pixel count
                return((boundingArea * viewportArea * projectionMatrix[0, 0] * projectionMatrix[1, 1]) / distanceSquared);
            }

            // break;
            case Projection.Orthographic:
            {
                // Compute orthographic area
                var orthoArea = camera.OrthoWindowHeight * camera.OrthoWindowWidth;

                // Check for 0 orthographic area
                if (orthoArea <= float.Epsilon)
                {
                    return(BaseValue);
                }

                // Estimate pixel count
                return((boundingArea * viewportArea) / orthoArea);
            }

            // break;
            default:
            {
                // This case is not covered for obvious reasons
                throw new NotSupportedException();
            }
            }
        }
Пример #2
0
        /// <summary>
        /// Sets the reference view upon which the distances were based.
        /// </summary>
        /// <note>
        /// This automatically enables use of the reference view.
        ///  There is no corresponding get method for these values as
        ///    they are not saved, but used to compute a reference value.
        /// </note>
        /// <param name="viewportWidth"></param>
        /// <param name="viewportHeight"></param>
        /// <param name="fovY"></param>
        public virtual void SetReferenceView(float viewportWidth, float viewportHeight, Radian fovY)
        {
            // Determine x FOV based on aspect ratio
            var fovX = fovY * ((Real)viewportWidth / (Real)viewportHeight);

            // Determine viewport area
            var viewportArea = viewportHeight * viewportWidth;

            // Compute reference view value based on viewport area and FOVs
            this.ReferenceViewValue = viewportArea * MathHelper.Tan(fovX * (Real)0.5f) * MathHelper.Tan(fovY * (Real)0.5f);

            // Enable use of reference view
            this._referenceViewEnabled = true;
        }
Пример #3
0
        protected override Real getValue(MovableObject movableObject, Camera cam)
        {
            // Get squared depth taking into account bounding radius
            // (d - r) ^ 2 = d^2 - 2dr + r^2, but this requires a lot
            // more computation (including a sqrt) so we approximate
            // it with d^2 - r^2, which is good enough for determining
            // lod.
            Real squaredDepth = movableObject.ParentNode.GetSquaredViewDepth(cam) -
                                MathHelper.Sqr(movableObject.BoundingRadius);

            // Check if reference view needs to be taken into account
            if (this._referenceViewEnabled)
            {
                // Reference view only applicable to perspective projection
                System.Diagnostics.Debug.Assert(cam.ProjectionType == Projection.Perspective,
                                                "Camera projection type must be perspective!");

                // Get camera viewport
                var viewport = cam.Viewport;

                // Get viewport area
                Real viewportArea = viewport.ActualWidth * viewport.ActualHeight;

                // Get projection matrix (this is done to avoid computation of tan(fov / 2))
                var projectionMatrix = cam.ProjectionMatrix;

                // Compute bias value (note that this is similar to the method used for PixelCountLodStrategy)
                Real biasValue = viewportArea * projectionMatrix[0, 0] * projectionMatrix[1, 1];

                // Scale squared depth appropriately
                squaredDepth *= (this.ReferenceViewValue / biasValue);
            }

            // Squared depth should never be below 0, so clamp
            squaredDepth = MathHelper.Max(squaredDepth, 0);

            // Now adjust it by the camera bias and return the computed value
            return(squaredDepth * cam.InverseLodBias);
        }
Пример #4
0
 public override Real TransformUserValue(Real userValue)
 {
     return(MathHelper.Sqr(userValue));
 }