/// <summary> /// Calculates exact intersection point (in uniform grid coordinates) from stored havok's hit info object obtained during FindClosest grid. /// Returns position of intersected object in uniform grid coordinates. /// </summary> protected Vector3D?GetIntersectedBlockData(ref MatrixD inverseGridWorldMatrix, out Vector3D intersection, out MySlimBlock intersectedBlock, out ushort?compoundBlockId) { Debug.Assert(m_hitInfo != null); Debug.Assert(m_hitInfo.Value.HkHitInfo.Body.GetEntity() == CurrentGrid); intersection = Vector3D.Zero; intersectedBlock = null; compoundBlockId = null; double distance = double.MaxValue; Vector3D?intersectedObjectPos = null; var line = new LineD(IntersectionStart, IntersectionStart + IntersectionDirection * IntersectionDistance); Vector3I position = Vector3I.Zero; if (!CurrentGrid.GetLineIntersectionExactGrid(ref line, ref position, ref distance, m_hitInfo.Value)) { return(null); } distance = Math.Sqrt(distance); intersectedObjectPos = position; intersectedBlock = CurrentGrid.GetCubeBlock(position); if (intersectedBlock == null) { return(null); } // Compound block - get index of internal block for removing if (intersectedBlock.FatBlock is MyCompoundCubeBlock) { MyCompoundCubeBlock compoundBlock = intersectedBlock.FatBlock as MyCompoundCubeBlock; ushort?idInCompound = null; ushort blockId; MyIntersectionResultLineTriangleEx?triIntersection; if (compoundBlock.GetIntersectionWithLine(ref line, out triIntersection, out blockId)) { idInCompound = blockId; } else if (compoundBlock.GetBlocksCount() == 1) // If not intersecting with any internal block and there is only one then set the index to it { idInCompound = compoundBlock.GetBlockId(compoundBlock.GetBlocks()[0]); } compoundBlockId = idInCompound; } Debug.Assert(intersectedObjectPos != null); Vector3D rayStart = Vector3D.Transform(IntersectionStart, inverseGridWorldMatrix); Vector3D rayDir = Vector3D.Normalize(Vector3D.TransformNormal(IntersectionDirection, inverseGridWorldMatrix)); intersection = rayStart + distance * rayDir; intersection *= 1.0f / CurrentGrid.GridSize; return(intersectedObjectPos); }
protected Vector3D?GetIntersectedBlockData(ref MatrixD inverseGridWorldMatrix, out Vector3D intersection, out MySlimBlock intersectedBlock, out ushort?compoundBlockId) { intersection = Vector3D.Zero; intersectedBlock = null; compoundBlockId = 0; if (this.CurrentGrid == null) { return(null); } double maxValue = double.MaxValue; Vector3D?nullable = null; LineD line = new LineD(IntersectionStart, IntersectionStart + (IntersectionDirection * IntersectionDistance)); Vector3I zero = Vector3I.Zero; if (!this.CurrentGrid.GetLineIntersectionExactGrid(ref line, ref zero, ref maxValue, new Sandbox.Engine.Physics.MyPhysics.HitInfo?(this.m_hitInfo.Value))) { return(null); } maxValue = Math.Sqrt(maxValue); nullable = new Vector3D?((Vector3D)zero); intersectedBlock = this.CurrentGrid.GetCubeBlock(zero); if (intersectedBlock == null) { return(null); } if (intersectedBlock.FatBlock is MyCompoundCubeBlock) { ushort num2; MyIntersectionResultLineTriangleEx?nullable4; MyCompoundCubeBlock fatBlock = intersectedBlock.FatBlock as MyCompoundCubeBlock; ushort?blockId = null; if (fatBlock.GetIntersectionWithLine(ref line, out nullable4, out num2, IntersectionFlags.ALL_TRIANGLES, false, false)) { blockId = new ushort?(num2); } else if (fatBlock.GetBlocksCount() == 1) { blockId = fatBlock.GetBlockId(fatBlock.GetBlocks()[0]); } compoundBlockId = blockId; } Vector3D vectord = Vector3D.Transform(IntersectionStart, (MatrixD)inverseGridWorldMatrix); intersection = vectord + (maxValue * Vector3D.Normalize(Vector3D.TransformNormal(IntersectionDirection, (MatrixD)inverseGridWorldMatrix))); intersection *= 1f / this.CurrentGrid.GridSize; return(nullable); }
/// <summary> /// Calculates exact intersection point (in uniform grid coordinates) from stored havok's hit info object obtained during FindClosest grid. /// Returns position of intersected object in uniform grid coordinates. /// </summary> protected Vector3D?GetIntersectedBlockData(ref MatrixD inverseGridWorldMatrix, out Vector3D intersection, out MySlimBlock intersectedBlock, out ushort?compoundBlockId) { Debug.Assert(m_hitInfo != null); Debug.Assert(m_hitInfo.Value.HkHitInfo.Body.GetEntity() == CurrentGrid); intersection = Vector3D.Zero; intersectedBlock = null; compoundBlockId = null; double distance = double.MaxValue; Vector3D?intersectedObjectPos = null; var line = new LineD(IntersectionStart, IntersectionStart + IntersectionDirection * IntersectionDistance); Vector3I position = Vector3I.Zero; if (!CurrentGrid.GetLineIntersectionExactGrid(ref line, ref position, ref distance, m_hitInfo.Value)) { return(null); } distance = Math.Sqrt(distance); intersectedObjectPos = position; intersectedBlock = CurrentGrid.GetCubeBlock(position); if (intersectedBlock == null) { return(null); } // Compound block - get index of internal block for removing if (intersectedBlock.FatBlock is MyCompoundCubeBlock) { MyCompoundCubeBlock compoundBlock = intersectedBlock.FatBlock as MyCompoundCubeBlock; ListReader <MySlimBlock> slimBlocksInCompound = compoundBlock.GetBlocks(); double distanceSquaredInCompound = double.MaxValue; ushort?idInCompound = null; for (int i = 0; i < slimBlocksInCompound.Count; ++i) { MySlimBlock cmpSlimBlock = slimBlocksInCompound.ItemAt(i); MyIntersectionResultLineTriangleEx?intersectionTriResult; if (cmpSlimBlock.FatBlock.GetIntersectionWithLine(ref line, out intersectionTriResult) && intersectionTriResult != null) { Vector3D startToIntersection = intersectionTriResult.Value.IntersectionPointInWorldSpace - IntersectionStart; double instrDistanceSq = startToIntersection.LengthSquared(); if (instrDistanceSq < distanceSquaredInCompound) { distanceSquaredInCompound = instrDistanceSq; idInCompound = compoundBlock.GetBlockId(cmpSlimBlock); } } } // If not intersecting with any internal block and there is only one then set the index to it if (idInCompound == null && compoundBlock.GetBlocksCount() == 1) { idInCompound = compoundBlock.GetBlockId(compoundBlock.GetBlocks()[0]); } compoundBlockId = idInCompound; } Debug.Assert(intersectedObjectPos != null); Vector3D rayStart = Vector3D.Transform(IntersectionStart, inverseGridWorldMatrix); Vector3D rayDir = Vector3D.Normalize(Vector3D.TransformNormal(IntersectionDirection, inverseGridWorldMatrix)); intersection = rayStart + distance * rayDir; intersection *= 1.0f / CurrentGrid.GridSize; return(intersectedObjectPos); }