Exemplo n.º 1
0
        private void ComputeCollisionPhysics(MyCubeGrid entity1, MyCubeGrid entity2, Vector3D collisionAvg)
        {
            var e1Physics  = ((IMyCubeGrid)entity1).Physics;
            var e2Physics  = ((IMyCubeGrid)entity2).Physics;
            var e1IsStatic = e1Physics.IsStatic;
            var e2IsStatic = e2Physics.IsStatic;

            float bMass;

            if (e1IsStatic)
            {
                bMass = float.MaxValue * 0.001f;
            }
            else
            {
                bMass = entity1.GetCurrentMass();
            }

            float sMass;

            if (e2IsStatic)
            {
                sMass = float.MaxValue * 0.001f;
            }
            else if (DsSet.Settings.FortifyShield && DsState.State.Enhancer)
            {
                sMass = entity2.GetCurrentMass() * 2;
            }
            else
            {
                sMass = entity2.GetCurrentMass();
            }
            var     bCom                 = e1Physics.CenterOfMassWorld;
            var     bMassRelation        = bMass / sMass;
            var     bRelationClamp       = MathHelper.Clamp(bMassRelation, 0, 1);
            var     bCollisionCorrection = Vector3D.Lerp(bCom, collisionAvg, bRelationClamp);
            Vector3 bVelAtPoint;

            e1Physics.GetVelocityAtPointLocal(ref bCollisionCorrection, out bVelAtPoint);

            var     sCom                 = e2IsStatic ? DetectionCenter : e2Physics.CenterOfMassWorld;
            var     sMassRelation        = sMass / bMass;
            var     sRelationClamp       = MathHelper.Clamp(sMassRelation, 0, 1);
            var     sCollisionCorrection = Vector3D.Lerp(sCom, collisionAvg, sRelationClamp);
            Vector3 sVelAtPoint;

            e2Physics.GetVelocityAtPointLocal(ref sCollisionCorrection, out sVelAtPoint);

            var momentum       = (bMass * bVelAtPoint) + (sMass * sVelAtPoint);
            var resultVelocity = momentum / (bMass + sMass);

            var bDir   = (resultVelocity - bVelAtPoint) * bMass;
            var bForce = Vector3D.Normalize(bCom - collisionAvg);

            var sDir   = (resultVelocity - sVelAtPoint) * sMass;
            var sforce = Vector3D.Normalize(sCom - collisionAvg);

            if (!e2IsStatic)
            {
                var collisionData = new MyCollisionPhysicsData
                {
                    Entity1              = entity1,
                    Entity2              = entity2,
                    E1IsStatic           = e1IsStatic,
                    E2IsStatic           = e2IsStatic,
                    E1IsHeavier          = e1IsStatic || bMass > sMass,
                    E2IsHeavier          = e2IsStatic || sMass > bMass,
                    Mass1                = bMass,
                    Mass2                = sMass,
                    Com1                 = bCom,
                    Com2                 = sCom,
                    CollisionCorrection1 = bCollisionCorrection,
                    CollisionCorrection2 = sCollisionCorrection,
                    ImpDirection1        = bDir,
                    ImpDirection2        = sDir,
                    Force1               = bForce,
                    Force2               = sforce,
                    CollisionAvg         = collisionAvg,
                };
                var collisionEvent = Session.Instance.CollisionPool.Get();
                collisionEvent.Init(collisionData, this);

                Session.Instance.ThreadEvents.Enqueue(collisionEvent);
            }
            else
            {
                var altMomentum       = (bMass * bVelAtPoint);
                var altResultVelocity = altMomentum / (bMass + (bMass * 0.5f));
                var bDir2             = (altResultVelocity - bVelAtPoint) * bMass;

                var     transformInv  = DetectMatrixOutsideInv;
                var     normalMat     = MatrixD.Transpose(transformInv);
                var     localNormal   = Vector3D.Transform(collisionAvg, transformInv);
                var     surfaceNormal = Vector3D.Normalize(Vector3D.TransformNormal(localNormal, normalMat));
                Vector3 velAtPoint;
                e1Physics.GetVelocityAtPointLocal(ref collisionAvg, out velAtPoint);
                var bSurfaceDir   = -Vector3D.Dot(velAtPoint, surfaceNormal) * surfaceNormal;
                var collisionData = new MyCollisionPhysicsData
                {
                    Entity1 = entity1,
                    Mass1   = bMass,
                    Com1    = bCom,
                    CollisionCorrection1 = bCollisionCorrection,
                    ImpDirection1        = bDir2,
                    ImpDirection2        = bSurfaceDir,
                    Force1       = bForce,
                    CollisionAvg = collisionAvg
                };

                var collisionEvent = Session.Instance.StaticCollisionPool.Get();
                collisionEvent.Init(collisionData, this);

                Session.Instance.ThreadEvents.Enqueue(collisionEvent);
            }
        }
Exemplo n.º 2
0
        public static void SmallIntersect(EntIntersectInfo entInfo, ConcurrentQueue <IMySlimBlock> fewDmgBlocks, ConcurrentQueue <IMySlimBlock> destroyedBlocks, ConcurrentQueue <MyAddForceData> force, ConcurrentQueue <MyImpulseData> impulse, MyCubeGrid grid, MatrixD matrix, MatrixD matrixInv, bool damageBlocks = true)
        {
            try
            {
                var contactPoint = ContactPointOutside(grid, matrix);
                if (!(Vector3D.Transform(contactPoint, matrixInv).LengthSquared() <= 1))
                {
                    return;
                }

                var getBlocks = new List <IMySlimBlock>();
                (grid as IMyCubeGrid).GetBlocks(getBlocks);
                var blockPoints  = new Vector3D[9];
                var collisionAvg = Vector3D.Zero;
                var c3           = 0;
                for (int i = 0; i < getBlocks.Count; i++)
                {
                    var block = getBlocks[i];
                    if (damageBlocks && block.IsDestroyed)
                    {
                        destroyedBlocks.Enqueue(block);
                        continue;
                    }

                    BoundingBoxD blockBox;
                    block.GetWorldBoundingBox(out blockBox);
                    blockBox.GetCorners(blockPoints);
                    blockPoints[8] = blockBox.Center;
                    for (int j = 8; j > -1; j--)
                    {
                        var point = blockPoints[j];
                        if (Vector3.Transform(point, matrixInv).LengthSquared() > 1)
                        {
                            continue;
                        }
                        c3++;
                        collisionAvg += point;
                        if (damageBlocks)
                        {
                            fewDmgBlocks.Enqueue(block);
                        }
                        break;
                    }
                }

                if (collisionAvg != Vector3D.Zero)
                {
                    collisionAvg        /= c3;
                    entInfo.ContactPoint = collisionAvg;
                    var mass = grid.GetCurrentMass();

                    var transformInv  = matrixInv;
                    var normalMat     = MatrixD.Transpose(transformInv);
                    var localNormal   = Vector3D.Transform(collisionAvg, transformInv);
                    var surfaceNormal = Vector3D.Normalize(Vector3D.TransformNormal(localNormal, normalMat));
                    var gridLinearVel = grid.Physics.LinearVelocity;
                    var gridLinearLen = gridLinearVel.Length();

                    var forceData = new MyAddForceData {
                        MyGrid = grid, Force = (grid.PositionComp.WorldAABB.Center - matrix.Translation) * (mass * gridLinearLen), MaxSpeed = MathHelper.Clamp(gridLinearLen, 10, gridLinearLen * 0.5f)
                    };
                    var impulseData = new MyImpulseData {
                        MyGrid = grid, Direction = mass * 0.015 * -Vector3D.Dot(gridLinearVel, surfaceNormal) * surfaceNormal, Position = collisionAvg
                    };
                    force.Enqueue(forceData);
                    impulse.Enqueue(impulseData);
                    entInfo.Damage = mass * 0.5f;
                }
            }
            catch (Exception ex) { Log.Line($"Exception in SmallIntersect: {ex}"); }
        }
Exemplo n.º 3
0
        private void CalculateShipCategory()
        {
            ShipTypeEnum originalType = m_shipCategory;

            if (m_shipThrusters == null && (m_shipWheels == null || m_shipWheels.WheelCount <= 0))
            {
                m_shipCategory = ShipTypeEnum.Debris;
            }
            else
            {
                bool hasController = false;
                foreach (var block in m_shipGrid.GetFatBlocks())
                {
                    if (block is MyShipController)
                    {
                        if (m_shipGrid.MainCockpit == null && m_shipGrid.GridSizeEnum == MyCubeSize.Small)
                        {
                            m_shipSoundSource = block as MyEntity;
                        }
                        hasController = true;
                        break;
                    }
                }
                if (hasController)
                {
                    int shipMass = m_shipGrid.GetCurrentMass();
                    if (shipMass >= SHIP_CATEGORY_MASS_HUGE)
                    {
                        m_shipCategory = ShipTypeEnum.Huge;
                    }
                    else if (shipMass >= SHIP_CATEGORY_MASS_LARGE)
                    {
                        m_shipCategory = ShipTypeEnum.Large;
                    }
                    else if (shipMass >= SHIP_CATEGORY_MASS_MEDIUM)
                    {
                        m_shipCategory = ShipTypeEnum.Medium;
                    }
                    else if (shipMass >= SHIP_CATEGORY_MASS_SMALL)
                    {
                        m_shipCategory = ShipTypeEnum.Small;
                    }
                    else if (shipMass >= SHIP_CATEGORY_MASS_TINY)
                    {
                        m_shipCategory = ShipTypeEnum.Tiny;
                    }
                    else
                    {
                        m_shipCategory = ShipTypeEnum.Debris;
                    }
                }
                else
                {
                    m_shipCategory = ShipTypeEnum.Debris;
                }
            }

            if (originalType != m_shipCategory)
            {
                m_categoryChange = true;
                if (m_shipCategory == ShipTypeEnum.Debris)
                {
                    for (int i = 0; i < m_emitters.Length; i++)
                    {
                        if (m_emitters[i].IsPlaying && m_emitters[i].Loop)
                        {
                            if (i == (int)ShipEmitters.WheelsMain || i == (int)ShipEmitters.WheelsSecondary)
                            {
                                m_emitters[i].StopSound(m_shipWheels == null);
                            }
                            else
                            {
                                m_emitters[i].StopSound(m_shipThrusters == null);
                            }
                        }
                    }
                }
                else
                {
                    for (int i = 0; i < m_emitters.Length; i++)
                    {
                        if (m_emitters[i].IsPlaying && m_emitters[i].Loop)
                        {
                            m_emitters[i].StopSound(true);
                        }
                    }
                }
            }
            if (m_shipCategory == ShipTypeEnum.Debris)
            {
                SetGridSounds(false);
            }
            else
            {
                SetGridSounds(true);
            }
        }
        private void RecreateControls()
        {
            Debug.Assert(m_infoPage != null, "Terminal page is null");
            if (m_infoPage == null)
            {
                return;
            }
            if (MyFakes.ENABLE_CENTER_OF_MASS)
            {
                var centerBtn = (MyGuiControlCheckbox)m_infoPage.Controls.GetControlByName("CenterBtn");
                centerBtn.IsChecked        = MyCubeGrid.ShowCenterOfMass;
                centerBtn.IsCheckedChanged = centerBtn_IsCheckedChanged;

                var pivotBtn = (MyGuiControlCheckbox)m_infoPage.Controls.GetControlByName("PivotBtn");
                pivotBtn.IsChecked        = MyCubeGrid.ShowGridPivot;
                pivotBtn.IsCheckedChanged = pivotBtn_IsCheckedChanged;
            }

            var showGravityGizmoBtn = (MyGuiControlCheckbox)m_infoPage.Controls.GetControlByName("ShowGravityGizmo");

            showGravityGizmoBtn.IsChecked        = MyCubeGrid.ShowGravityGizmos;
            showGravityGizmoBtn.IsCheckedChanged = showGravityGizmos_IsCheckedChanged;

            var showSenzorGizmoBtn = (MyGuiControlCheckbox)m_infoPage.Controls.GetControlByName("ShowSenzorGizmo");

            showSenzorGizmoBtn.IsChecked        = MyCubeGrid.ShowSenzorGizmos;
            showSenzorGizmoBtn.IsCheckedChanged = showSenzorGizmos_IsCheckedChanged;

            var showAntenaGizmoBtn = (MyGuiControlCheckbox)m_infoPage.Controls.GetControlByName("ShowAntenaGizmo");

            showAntenaGizmoBtn.IsChecked        = MyCubeGrid.ShowAntennaGizmos;
            showAntenaGizmoBtn.IsCheckedChanged = showAntenaGizmos_IsCheckedChanged;

            var friendAntennaRange = (MyGuiControlSlider)m_infoPage.Controls.GetControlByName("FriendAntennaRange");

            friendAntennaRange.Value         = MyHudMarkerRender.FriendAntennaRange;
            friendAntennaRange.ValueChanged += (MyGuiControlSlider s) => { MyHudMarkerRender.FriendAntennaRange = s.Value; };


            var enemyAntennaRange = (MyGuiControlSlider)m_infoPage.Controls.GetControlByName("EnemyAntennaRange");

            enemyAntennaRange.Value         = MyHudMarkerRender.EnemyAntennaRange;
            enemyAntennaRange.ValueChanged += (MyGuiControlSlider s) => { MyHudMarkerRender.EnemyAntennaRange = s.Value; };

            var ownedAntennaRange = (MyGuiControlSlider)m_infoPage.Controls.GetControlByName("OwnedAntennaRange");

            ownedAntennaRange.Value         = MyHudMarkerRender.OwnerAntennaRange;
            ownedAntennaRange.ValueChanged += (MyGuiControlSlider s) => { MyHudMarkerRender.OwnerAntennaRange = s.Value; };

            if (MyFakes.ENABLE_TERMINAL_PROPERTIES)
            {
                var renameShipLabel = (MyGuiControlLabel)m_infoPage.Controls.GetControlByName("RenameShipLabel");

                var renameShipBtn = (MyGuiControlButton)m_infoPage.Controls.GetControlByName("RenameShipButton");

                var renameShipText = (MyGuiControlTextbox)m_infoPage.Controls.GetControlByName("RenameShipText");
                if (renameShipText != null && m_grid != null)
                {
                    renameShipText.Text = m_grid.DisplayName;
                }

                var showRenameShip = IsPlayerOwner(m_grid);
                renameShipLabel.Visible = showRenameShip;
                renameShipBtn.Visible   = showRenameShip;
                renameShipText.Visible  = showRenameShip;
            }

            var convertBtn        = (MyGuiControlButton)m_infoPage.Controls.GetControlByName("ConvertBtn");
            MyGuiControlList list = (MyGuiControlList)m_infoPage.Controls.GetControlByName("InfoList");

            list.Controls.Clear();

            if (m_grid == null || m_grid.Physics == null)
            {
                convertBtn.Enabled = false;
                MyGuiControlLabel noShip = new MyGuiControlLabel(text: MyTexts.GetString(MySpaceTexts.ScreenTerminalError_ShipNotConnected), font: MyFontEnum.Red);
                list.Controls.Add(noShip);
                return;
            }

            if (!m_grid.IsStatic || m_grid.MarkedForClose)
            {
                convertBtn.Enabled = false;
            }

            if (!m_grid.BigOwners.Contains(MySession.Static.LocalPlayerId))
            {
                convertBtn.Enabled = false;
            }

            var setDestructibleBlocks = (MyGuiControlCheckbox)m_infoPage.Controls.GetControlByName("SetDestructibleBlocks");

            setDestructibleBlocks.IsChecked        = m_grid.DestructibleBlocks;
            setDestructibleBlocks.Visible          = MySession.Static.Settings.ScenarioEditMode || MySession.Static.IsScenario;
            setDestructibleBlocks.Enabled          = MySession.Static.Settings.ScenarioEditMode;
            setDestructibleBlocks.IsCheckedChanged = setDestructibleBlocksBtn_IsCheckedChanged;

            int gravityCounter = 0;

            if (m_grid.BlocksCounters.ContainsKey(typeof(MyObjectBuilder_GravityGenerator)))
            {
                gravityCounter = m_grid.BlocksCounters[typeof(MyObjectBuilder_GravityGenerator)];
            }
            int massCounter = 0;

            if (m_grid.BlocksCounters.ContainsKey(typeof(MyObjectBuilder_VirtualMass)))
            {
                massCounter = m_grid.BlocksCounters[typeof(MyObjectBuilder_VirtualMass)];
            }
            int lightCounter = 0;

            if (m_grid.BlocksCounters.ContainsKey(typeof(MyObjectBuilder_InteriorLight)))
            {
                lightCounter = m_grid.BlocksCounters[typeof(MyObjectBuilder_InteriorLight)];
            }
            var conveyorCounter = 0;

            foreach (var key in m_grid.BlocksCounters.Keys)
            {
                Type blockType = MyCubeBlockFactory.GetProducedType(key);
                if (typeof(IMyConveyorSegmentBlock).IsAssignableFrom(blockType) || typeof(IMyConveyorEndpointBlock).IsAssignableFrom(blockType))
                {
                    conveyorCounter += m_grid.BlocksCounters[key];
                }
            }
            int polygonCounter = 0;

            foreach (var block in m_grid.GetBlocks())
            {
                if (block.FatBlock != null)
                {
                    polygonCounter += block.FatBlock.Model.GetTrianglesCount();
                }
            }
            foreach (var cell in m_grid.RenderData.Cells.Values)
            {
                foreach (var part in cell.CubeParts)
                {
                    polygonCounter += part.Model.GetTrianglesCount();
                }
            }

            int thrustCount = 0;
            var thrustComp  = m_grid.Components.Get <MyEntityThrustComponent>();

            if (thrustComp != null)
            {
                thrustCount = thrustComp.ThrustCount;
            }
            MyGuiControlLabel thrustCountLabel = new MyGuiControlLabel(text: new StringBuilder().AppendStringBuilder(MyTexts.Get(MySpaceTexts.TerminalTab_Info_Thrusters)).AppendInt32(thrustCount).ToString());

            MyGuiControlLabel polygonCount = new MyGuiControlLabel(text: new StringBuilder().AppendStringBuilder(MyTexts.Get(MySpaceTexts.TerminalTab_Info_Triangles)).AppendInt32(polygonCounter).ToString());

            polygonCount.SetToolTip(MySpaceTexts.TerminalTab_Info_TrianglesTooltip);
            MyGuiControlLabel cubeCount = new MyGuiControlLabel(text: new StringBuilder().AppendStringBuilder(MyTexts.Get(MySpaceTexts.TerminalTab_Info_Blocks)).AppendInt32(m_grid.GetBlocks().Count).ToString());

            cubeCount.SetToolTip(MySpaceTexts.TerminalTab_Info_BlocksTooltip);
            MyGuiControlLabel blockCount     = new MyGuiControlLabel(text: new StringBuilder().AppendStringBuilder(MyTexts.Get(MySpaceTexts.TerminalTab_Info_NonArmor)).AppendInt32(m_grid.Hierarchy.Children.Count).ToString());
            MyGuiControlLabel lightCount     = new MyGuiControlLabel(text: new StringBuilder().Clear().AppendStringBuilder(MyTexts.Get(MySpaceTexts.TerminalTab_Info_Lights)).AppendInt32(lightCounter).ToString());
            MyGuiControlLabel reflectorCount = new MyGuiControlLabel(text: new StringBuilder().AppendStringBuilder(MyTexts.Get(MySpaceTexts.TerminalTab_Info_Reflectors)).AppendInt32(m_grid.GridSystems.ReflectorLightSystem.ReflectorCount).ToString());
            //MyGuiControlLabel wheelCount = new MyGuiControlLabel(text: new StringBuilder().AppendStringBuilder(MyTexts.Get(MySpaceTexts.TerminalTab_Info_Rotors)).AppendInt32(m_grid.WheelSystem.WheelCount));
            MyGuiControlLabel gravityCount  = new MyGuiControlLabel(text: new StringBuilder().AppendStringBuilder(MyTexts.Get(MySpaceTexts.TerminalTab_Info_GravGens)).AppendInt32(gravityCounter).ToString());
            MyGuiControlLabel massCount     = new MyGuiControlLabel(text: new StringBuilder().AppendStringBuilder(MyTexts.Get(MySpaceTexts.TerminalTab_Info_VirtualMass)).AppendInt32(massCounter).ToString());
            MyGuiControlLabel conveyorCount = new MyGuiControlLabel(text: new StringBuilder().AppendStringBuilder(MyTexts.Get(MySpaceTexts.TerminalTab_Info_Conveyors)).AppendInt32(conveyorCounter).ToString());
            var         mainCockpit         = m_grid.MainCockpit as MyShipController;
            MyCharacter pilot = null;

            if (mainCockpit != null)
            {
                pilot = mainCockpit.Pilot;
            }
            MyGuiControlLabel gridMass = new MyGuiControlLabel(text: new StringBuilder().AppendStringBuilder(MyTexts.Get(MySpaceTexts.TerminalTab_Info_GridMass)).AppendInt32(m_grid.GetCurrentMass(pilot)).ToString());

            list.InitControls(new MyGuiControlBase[] { cubeCount, blockCount, conveyorCount, thrustCountLabel, lightCount, reflectorCount, gravityCount, massCount, polygonCount, gridMass });
        }
        private void CalculateShipCategory()
        {
            bool           originalDebris = m_isDebris;
            MyDefinitionId originalType   = m_shipCategory;

            if (m_shipThrusters == null && (m_shipWheels == null || m_shipWheels.WheelCount <= 0))
            {
                m_isDebris = true;
            }
            else if (m_shipGrid.GridSystems.GyroSystem.GyroCount == 0)
            {
                m_isDebris = true;
            }
            else
            {
                bool hasController = false;
                foreach (var block in m_shipGrid.GetFatBlocks())
                {
                    if (block is MyShipController)
                    {
                        if (m_shipGrid.MainCockpit == null && m_shipGrid.GridSizeEnum == MyCubeSize.Small)
                        {
                            m_shipSoundSource = block as MyEntity;
                        }
                        hasController = true;
                        break;
                    }
                }
                if (hasController)
                {
                    int   shipMass   = m_shipGrid.GetCurrentMass();
                    float bestWeight = float.MinValue;
                    foreach (var group in m_categories.Values)
                    {
                        if (group.MinWeight < shipMass && ((group.AllowSmallGrid && m_shipGrid.GridSizeEnum == MyCubeSize.Small) || (group.AllowLargeGrid && m_shipGrid.GridSizeEnum == MyCubeSize.Large)))
                        {
                            if (bestWeight == float.MinValue || group.MinWeight > bestWeight)
                            {
                                bestWeight     = group.MinWeight;
                                m_shipCategory = group.Id;
                                m_groupData    = group;
                            }
                        }
                    }
                    if (bestWeight == float.MinValue)
                    {
                        m_isDebris = true;
                    }
                    else
                    {
                        m_isDebris = false;
                    }
                }
                else
                {
                    m_isDebris = true;
                }
            }
            if (m_groupData == null)
            {
                m_isDebris = true;
            }

            if (originalType != m_shipCategory || m_isDebris != originalDebris)
            {
                m_categoryChange = true;
                if (m_isDebris)
                {
                    for (int i = 0; i < m_emitters.Length; i++)
                    {
                        if (m_emitters[i].IsPlaying && m_emitters[i].Loop)
                        {
                            if (i == (int)ShipEmitters.WheelsMain || i == (int)ShipEmitters.WheelsSecondary)
                            {
                                m_emitters[i].StopSound(m_shipWheels == null);
                            }
                            else
                            {
                                m_emitters[i].StopSound(m_shipThrusters == null);
                            }
                        }
                    }
                }
                else
                {
                    for (int i = 0; i < m_emitters.Length; i++)
                    {
                        if (m_emitters[i].IsPlaying && m_emitters[i].Loop)
                        {
                            m_emitters[i].StopSound(true);
                        }
                    }
                }
            }
            if (m_isDebris)
            {
                SetGridSounds(false);
            }
            else
            {
                SetGridSounds(true);
            }
        }
Exemplo n.º 6
0
        private void ComputeVoxelPhysics(MyEntity entity1, MyCubeGrid entity2, Vector3D collisionAvg)
        {
            var e2Physics  = ((IMyCubeGrid)entity2).Physics;
            var e2IsStatic = e2Physics.IsStatic;

            float bMass;

            if (e2IsStatic)
            {
                bMass = float.MaxValue * 0.001f;
            }
            else
            {
                bMass = entity2.GetCurrentMass();
            }

            var sMass = float.MaxValue * 0.001f;

            var     bCom                 = e2Physics.CenterOfMassWorld;
            var     bMassRelation        = bMass / sMass;
            var     bRelationClamp       = MathHelper.Clamp(bMassRelation, 0, 1);
            var     bCollisionCorrection = Vector3D.Lerp(bCom, collisionAvg, bRelationClamp);
            Vector3 bVelAtPoint;

            e2Physics.GetVelocityAtPointLocal(ref bCollisionCorrection, out bVelAtPoint);

            var momentum       = (bMass * bVelAtPoint) + (sMass * 0);
            var resultVelocity = momentum / (bMass + sMass);

            var bDir   = (resultVelocity - bVelAtPoint) * bMass;
            var bForce = Vector3D.Normalize(bCom - collisionAvg);

            var collisionData = new MyCollisionPhysicsData
            {
                Entity1              = entity1,
                Entity2              = entity2,
                E1IsStatic           = true,
                E2IsStatic           = false,
                E1IsHeavier          = true,
                E2IsHeavier          = false,
                Mass1                = sMass,
                Mass2                = bMass,
                Com1                 = Vector3D.Zero,
                Com2                 = bCom,
                CollisionCorrection1 = Vector3D.Zero,
                CollisionCorrection2 = bCollisionCorrection,
                ImpDirection1        = Vector3D.Zero,
                ImpDirection2        = bDir,
                ImpPosition1         = Vector3D.Zero,
                ImpPosition2         = bCollisionCorrection,
                Force1               = Vector3D.Zero,
                Force2               = bForce,
                ForcePos1            = null,
                ForcePos2            = null,
                ForceTorque1         = null,
                ForceTorque2         = null,
                CollisionAvg         = collisionAvg,
                Immediate            = false
            };
            var collisionEvent = Session.Instance.VoxelCollisionPhysicsPool.Get();

            collisionEvent.Init(collisionData, this);
            Session.Instance.ThreadEvents.Enqueue(collisionEvent);
        }