コード例 #1
0
        // Checks distance to plane along axis.
        private bool TestAxis(int x, int y, int z)
        {
            Vector3I v           = new Vector3I(x, y, z);
            int      numerator   = normal.Dot(a - Coords);
            int      denominator = normal.Dot(v);

            if (denominator == 0)
            {
                return(numerator == 0);
            }
            double distance = ( double )numerator / denominator;

            return(distance > -0.5 && distance <= 0.5);
        }
コード例 #2
0
        private static void CheckStepVectors(Vector3I up)
        {
            var stepVectors = new StepVectors(up);

            // Sides are perpendicular to the Up vector (dot product is zero)
            foreach (var side in stepVectors.EnumerateSides())
            {
                Assert.Equal(0, Vector3I.Dot(up, side));
            }

            // All directions are unit vectors and they are different from each other.
            for (int i = 0; i < StepVectors.Count; i++)
            {
                var step = stepVectors.Steps[i];

                Assert.Equal(1, step.RectangularLength());

                for (int j = 0; j < StepVectors.Count; j++)  // Check all are different.
                {
                    if (j != i)
                    {
                        Assert.False(step.Equals(stepVectors.Steps[j]));
                    }
                }
            }
        }
コード例 #3
0
 private void FixSnapTransformationBase6()
 {
     if (base.CopiedGrids.Count != 0)
     {
         MyCubeGrid hitEntity = base.m_hitEntity as MyCubeGrid;
         if (hitEntity != null)
         {
             Matrix rotationDeltaMatrixToHitGrid = this.GetRotationDeltaMatrixToHitGrid(hitEntity);
             foreach (MyCubeGrid local1 in base.PreviewGrids)
             {
                 MatrixD worldMatrix = local1.WorldMatrix;
                 Matrix  matrix2     = (Matrix)(worldMatrix.GetOrientation() * rotationDeltaMatrixToHitGrid);
                 MatrixD xd          = MatrixD.CreateWorld(base.m_pastePosition, matrix2.Forward, matrix2.Up);
                 local1.PositionComp.SetWorldMatrix(xd, null, false, true, true, false, false, false);
             }
             if ((hitEntity.GridSizeEnum == MyCubeSize.Large) && (base.PreviewGrids[0].GridSizeEnum == MyCubeSize.Small))
             {
                 base.m_pastePosition = hitEntity.GridIntegerToWorld(MyCubeBuilder.TransformLargeGridHitCoordToSmallGrid(base.m_hitPos, hitEntity.PositionComp.WorldMatrixNormalizedInv, hitEntity.GridSize));
             }
             else
             {
                 Vector3I vectori    = Vector3I.Round(base.m_hitNormal);
                 Vector3I gridOffset = hitEntity.WorldToGridInteger(base.m_pastePosition);
                 Vector3I min        = base.PreviewGrids[0].Min;
                 Vector3I vectori4   = Vector3I.Abs(Vector3I.Round(Vector3D.TransformNormal(Vector3D.TransformNormal((Vector3D)((base.PreviewGrids[0].Max - min) + Vector3I.One), base.PreviewGrids[0].WorldMatrix), hitEntity.PositionComp.WorldMatrixNormalizedInv)));
                 int      num        = Math.Abs(Vector3I.Dot(ref vectori, ref vectori4));
                 int      num2       = 0;
                 while (true)
                 {
                     if ((num2 >= num) || hitEntity.CanMergeCubes(base.PreviewGrids[0], gridOffset))
                     {
                         if (num2 == num)
                         {
                             gridOffset = hitEntity.WorldToGridInteger(base.m_pastePosition);
                         }
                         base.m_pastePosition = hitEntity.GridIntegerToWorld(gridOffset);
                         break;
                     }
                     gridOffset = (Vector3I)(gridOffset + vectori);
                     num2++;
                 }
             }
             for (int i = 0; i < base.PreviewGrids.Count; i++)
             {
                 MyCubeGrid local2      = base.PreviewGrids[i];
                 MatrixD    worldMatrix = local2.WorldMatrix;
                 worldMatrix.Translation = base.m_pastePosition + Vector3.Transform(base.m_copiedGridOffsets[i], rotationDeltaMatrixToHitGrid);
                 local2.PositionComp.SetWorldMatrix(worldMatrix, null, false, true, true, false, false, false);
             }
             if (MyDebugDrawSettings.DEBUG_DRAW_COPY_PASTE)
             {
                 MyRenderProxy.DebugDrawLine3D(base.m_hitPos, base.m_hitPos + base.m_hitNormal, Color.Red, Color.Green, false, false);
             }
         }
     }
 }
コード例 #4
0
 public Vector3I Mark(Vector3I pos, IMySlimBlock block, char mark = '▓') {
     var projected = pos * planeIsh;
     map[projected] = mark;
     int alongWide = wide.Dot(ref pos);
     int alongHigh = high.Dot(ref pos);
     if(alongWide < wideLow) wideLow = alongWide;
     if(alongWide > wideHigh) wideHigh = alongWide;
     if(alongHigh < highLow) highLow = alongHigh;
     if(alongHigh > highHigh) highHigh = alongHigh;        
     return projected;
 }
コード例 #5
0
        /// <summary>
        /// Move air by velocity.
        /// </summary>
        private void MoveAir()
        {
            Profiler.StartProfileBlock();
            Log.TraceLog("entered");
            int dirDim = m_shipDirection.Max() == 0 ? 0 : m_sizeCell.Dot(ref m_shipDirection) - 1;

            Vector3I index;

            for (index.X = 0; index.X < m_sizeCell.X; index.X++)
            {
                for (index.Y = 0; index.Y < m_sizeCell.Y; index.Y++)
                {
                    for (index.Z = 0; index.Z < m_sizeCell.Z; index.Z++)
                    {
                        AeroCell currentData;
                        GetValue(ref index, out currentData);
                        if (!currentData.Process)
                        {
                            continue;
                        }

                        Vector3I currentCell = index + m_minCell;
                        //Vector3 currentCellF = currentCell;

                        Vector3 targetCellAvg = currentCell + currentData.CurVelocity;
                        //Vector3.Add(ref currentCellF, ref currentData.MoveVelocity, out targetCellAvg);

                        if (!currentData.BlockTest)
                        {
                            BlockTest(currentData, ref currentCell, ref targetCellAvg);
                        }

                        PushAir(ref currentCell, currentData, ref targetCellAvg);

                        int dot; Vector3I.Dot(ref index, ref m_shipDirection, out dot);
                        if (dot == dirDim)
                        {
                            currentData.NextAirPress += m_defaultData.CurAirPress;
                        }

                        Log.TraceLog("Cell: " + currentCell + ", " + currentData, condition: currentData.LogChange);
                    }
                }
            }
            Log.TraceLog("exiting");
            Profiler.EndProfileBlock();
        }
コード例 #6
0
        private void GenerateBlockSphere(MyCubeSize gridSizeEnum, double radiusInMeters)
        {
            var gridSizeInv = 2.0; // Assume small grid (1 / 0.5)

            if (gridSizeEnum == MyCubeSize.Large)
            {
                gridSizeInv = 0.4; // Large grid (1 / 2.5)
            }
            var radiusInBlocks = radiusInMeters * gridSizeInv;
            var radiusSq = radiusInBlocks * radiusInBlocks;
            var radiusCeil = (int)Math.Ceiling(radiusInBlocks);
            int i, j, k;
            var max = Vector3I.One * radiusCeil;
            var min = Vector3I.One * -radiusCeil;

            var blockSphereLst = _blockSpherePool.Get();

            for (i = min.X; i <= max.X; ++i)
            {
                for (j = min.Y; j <= max.Y; ++j)
                {
                    for (k = min.Z; k <= max.Z; ++k)
                    {
                        if (i * i + j * j + k * k < radiusSq)
                        {
                            blockSphereLst.Add(new Vector3I(i, j, k));
                        }
                    }
                }
            }

            blockSphereLst.Sort((a, b) => Vector3I.Dot(a, a).CompareTo(Vector3I.Dot(b, b)));
            if (gridSizeEnum == MyCubeSize.Large)
            {
                LargeBlockSphereDb.Add(radiusInMeters, blockSphereLst);
            }
            else
            {
                SmallBlockSphereDb.Add(radiusInMeters, blockSphereLst);
            }
        }
コード例 #7
0
        private void GetIntVectorsInSphere2(MyCubeGrid grid, Vector3I center, double radius)
        {
            _slimsSortedList.Clear();
            radius *= grid.GridSizeR;
            var      gridMin = grid.Min;
            var      gridMax = grid.Max;
            double   radiusSq = radius * radius;
            int      radiusCeil = (int)Math.Ceiling(radius);
            int      i, j, k;
            Vector3I max = Vector3I.Min(Vector3I.One * radiusCeil, gridMax - center);
            Vector3I min = Vector3I.Max(Vector3I.One * -radiusCeil, gridMin - center);

            for (i = min.X; i <= max.X; ++i)
            {
                for (j = min.Y; j <= max.Y; ++j)
                {
                    for (k = min.Z; k <= max.Z; ++k)
                    {
                        if (i * i + j * j + k * k < radiusSq)
                        {
                            var          vector3I = center + new Vector3I(i, j, k);
                            IMySlimBlock slim     = grid.GetCubeBlock(vector3I);

                            if (slim != null && slim.Position == vector3I)
                            {
                                var radiatedBlock = new RadiatedBlock
                                {
                                    Center = center, Slim = slim, Position = vector3I
                                };
                                _slimsSortedList.Add(radiatedBlock);
                            }
                        }
                    }
                }
            }
            _slimsSortedList.Sort((a, b) => Vector3I.Dot(a.Position, a.Position).CompareTo(Vector3I.Dot(b.Position, b.Position)));
        }
コード例 #8
0
ファイル: Corridor.cs プロジェクト: Hellothere-1/SE
            public bool IsInCorridor(IMyCubeBlock block)
            {
                Vector3I v1 = block.Position - position;

                return(Vector3I.Dot(v1, Base6Directions.GetIntVector(core.Orientation.Up)) == 0 && Vector3I.Dot(v1, Base6Directions.GetIntVector(core.Orientation.Left)) == 0);
            }
コード例 #9
0
        private new void FixSnapTransformationBase6()
        {
            Debug.Assert(CopiedGrids.Count > 0);
            if (CopiedGrids.Count == 0)
            {
                return;
            }

            var hitGrid = m_hitEntity as MyCubeGrid;

            if (hitGrid == null)
            {
                return;
            }

            // Fix rotation of the first pasted grid
            Matrix hitGridRotation  = hitGrid.WorldMatrix.GetOrientation();
            Matrix firstRotation    = PreviewGrids[0].WorldMatrix.GetOrientation();
            Matrix newFirstRotation = Matrix.AlignRotationToAxes(ref firstRotation, ref hitGridRotation);
            Matrix rotationDelta    = Matrix.Invert(firstRotation) * newFirstRotation;

            foreach (var grid in PreviewGrids)
            {
                Matrix rotation = grid.WorldMatrix.GetOrientation();
                rotation = rotation * rotationDelta;
                Matrix rotationInv = Matrix.Invert(rotation);

                Vector3D position = m_pastePosition;

                MatrixD newWorld = MatrixD.CreateWorld(position, rotation.Forward, rotation.Up);
                Debug.Assert(newWorld.GetOrientation().IsRotation());
                grid.PositionComp.SetWorldMatrix(newWorld);
            }

            bool smallOnLargeGrid = hitGrid.GridSizeEnum == MyCubeSize.Large && PreviewGrids[0].GridSizeEnum == MyCubeSize.Small;

            if (smallOnLargeGrid)
            {
                Vector3 pasteOffset = TransformLargeGridHitCoordToSmallGrid(m_hitPos, hitGrid.PositionComp.WorldMatrixNormalizedInv, hitGrid.GridSize);
                m_pastePosition = hitGrid.GridIntegerToWorld(pasteOffset);
            }
            else
            {
                // Find a collision-free position for the first paste grid along the raycast normal
                Vector3I collisionTestStep        = Vector3I.Round(m_hitNormal);
                Vector3I pasteOffset              = hitGrid.WorldToGridInteger(m_pastePosition);
                Vector3I previewGridMin           = PreviewGrids[0].Min;
                Vector3I previewGridMax           = PreviewGrids[0].Max;
                Vector3I previewGridSize          = previewGridMax - previewGridMin + Vector3I.One;
                Vector3D previewGridSizeInWorld   = Vector3D.TransformNormal((Vector3D)previewGridSize, PreviewGrids[0].WorldMatrix);
                Vector3I previewGridSizeInHitGrid = Vector3I.Abs(Vector3I.Round(Vector3D.TransformNormal(previewGridSizeInWorld, hitGrid.PositionComp.WorldMatrixNormalizedInv)));

                int attemptsCount = Math.Abs(Vector3I.Dot(ref collisionTestStep, ref previewGridSizeInHitGrid));
                Debug.Assert(attemptsCount > 0);
                int i;

                for (i = 0; i < attemptsCount; ++i)
                {
                    if (hitGrid.CanMergeCubes(PreviewGrids[0], pasteOffset))
                    {
                        break;
                    }
                    pasteOffset += collisionTestStep;
                }

                if (i == attemptsCount)
                {
                    pasteOffset = hitGrid.WorldToGridInteger(m_pastePosition);
                }

                m_pastePosition = hitGrid.GridIntegerToWorld(pasteOffset);
            }

            // Move all the grids according to the collision-free position of the first one
            for (int i = 0; i < PreviewGrids.Count; ++i)
            {
                var     grid   = PreviewGrids[i];
                MatrixD matrix = grid.WorldMatrix;
                matrix.Translation = m_pastePosition + Vector3.Transform(m_copiedGridOffsets[i], rotationDelta);
                grid.PositionComp.SetWorldMatrix(matrix);
            }

            if (MyDebugDrawSettings.DEBUG_DRAW_COPY_PASTE)
            {
                MyRenderProxy.DebugDrawLine3D(m_hitPos, m_hitPos + m_hitNormal, Color.Red, Color.Green, false);
            }
        }
コード例 #10
0
ファイル: IMyCubeGridExtensions.cs プロジェクト: zrisher/ARMS
        /// <summary>
        /// Yields the first occupied cells encountered when raycasting a grid in a given base direction.
        /// </summary>
        /// <param name="grid">The grid to get blocks from.</param>
        /// <param name="baseDirection">The direction of ray.</param>
        public static IEnumerable <Vector3I> FirstBlocks(this IMyCubeGrid grid, Vector3I baseDirection)
        {
            Logger.DebugLog("baseDirection(" + baseDirection + ") has a magnitude", Logger.severity.FATAL, condition: baseDirection.RectangularLength() != 1);

            BoundingBox localAABB = grid.LocalAABB;

            Vector3I min = grid.Min, max = grid.Max;

            // ???
            //Vector3 minF; Vector3.Divide(ref localAABB.Min, grid.GridSize, out minF);
            //Vector3 maxF; Vector3.Divide(ref localAABB.Max, grid.GridSize, out maxF);
            //Vector3I min, max;

            //Func<float, int> round = f => (int)Math.Round(f);
            //minF.ApplyOperation(round, out min);
            //maxF.ApplyOperation(round, out max);

            Vector3I perp0, perp1;

            perp0 = Base6Directions.GetIntVector(Base6Directions.GetPerpendicular(Base6Directions.GetDirection(baseDirection)));
            Vector3I.Cross(ref baseDirection, ref perp0, out perp1);

            int baseStart; Vector3I.Dot(ref baseDirection, ref min, out baseStart);
            int baseEnd; Vector3I.Dot(ref baseDirection, ref max, out baseEnd);

            if (baseStart > baseEnd)
            {
                int temp = baseStart;
                baseStart = baseEnd;
                baseEnd   = temp;
            }
            bool incrementBase = baseStart <= baseEnd;

            int perp0Min; Vector3I.Dot(ref perp0, ref min, out perp0Min);
            int perp0Max; Vector3I.Dot(ref perp0, ref max, out perp0Max);

            if (perp0Max < perp0Min)
            {
                int temp = perp0Max;
                perp0Max = perp0Min;
                perp0Min = temp;
            }

            int perp1Min; Vector3I.Dot(ref perp1, ref min, out perp1Min);
            int perp1Max; Vector3I.Dot(ref perp1, ref max, out perp1Max);

            if (perp1Max < perp1Min)
            {
                int temp = perp1Max;
                perp1Max = perp1Min;
                perp1Min = temp;
            }

            Logger.TraceLog("min: " + min + ", max: " + max, Logger.severity.DEBUG);
            Logger.TraceLog("base: " + baseDirection + ", perp0: " + perp0 + ", perp1: " + perp1, Logger.severity.DEBUG);
            Logger.TraceLog("base range: " + baseStart + ":" + baseEnd, Logger.severity.DEBUG);
            Logger.TraceLog("perp0 range: " + perp0Min + ":" + perp0Max, Logger.severity.DEBUG);
            Logger.TraceLog("perp1 range: " + perp1Min + ":" + perp1Max, Logger.severity.DEBUG);

            for (int perp0Value = perp0Min; perp0Value <= perp0Max; perp0Value++)
            {
                for (int perp1Value = perp1Min; perp1Value <= perp1Max; perp1Value++)
                {
                    int baseValue = baseStart;
                    while (true)
                    {
                        Vector3I cell = baseValue * baseDirection + perp0Value * perp0 + perp1Value * perp1;

                        if (grid.CubeExists(cell))
                        {
                            yield return(cell);

                            break;
                        }

                        if (baseValue == baseEnd)
                        {
                            break;
                        }
                        if (incrementBase)
                        {
                            baseValue++;
                        }
                        else
                        {
                            baseValue--;
                        }
                    }
                }
            }

            yield break;
        }
コード例 #11
0
        public void Dot()
        {
            Vector3I a = new Vector3I(1, 2, 3);
            Vector3I b = new Vector3I(4, 5, 6);

            double dot = a.Dot(b);
            Assert.AreEqual(1 * 4 + 2 * 5 + 3 * 6, dot, 1e-14);
        }