Beispiel #1
0
        private static ClampingInfo CheckForClamping(Vector3I originalValue, Vector3I clampedValue)
        {
            ClampingInfo info = new ClampingInfo(false, false, false);

            if (originalValue.X != clampedValue.X)
            {
                info.X = true;
            }
            if (originalValue.Y != clampedValue.Y)
            {
                info.Y = true;
            }
            if (originalValue.Z != clampedValue.Z)
            {
                info.Z = true;
            }
            return(info);
        }
Beispiel #2
0
        public static ulong FillInShape(MyVoxelBase voxelMap, MyShape shape, byte materialIdx)
        {
            Vector3I minCorner, maxCorner, numCells;
            ulong    retValue = 0;

            GetVoxelShapeDimensions(voxelMap, shape, out minCorner, out maxCorner, out numCells);

            //voxel must be at least 1 m from side to be closed (e.g. without holes in it)
            minCorner = Vector3I.Max(Vector3I.One, minCorner);
            maxCorner = Vector3I.Max(minCorner, maxCorner);

            for (var itCells = new Vector3I_RangeIterator(ref Vector3I.Zero, ref numCells); itCells.IsValid(); itCells.MoveNext())
            {
                Vector3I cellMinCorner, cellMaxCorner;
                GetCellCorners(ref minCorner, ref maxCorner, ref itCells, out cellMinCorner, out cellMaxCorner);

                Vector3I originalMinCorner = cellMinCorner;
                Vector3I originalMaxCorner = cellMaxCorner;

                voxelMap.Storage.ClampVoxelCoord(ref cellMinCorner, 0);
                voxelMap.Storage.ClampVoxelCoord(ref cellMaxCorner, 0);

                ClampingInfo minCornerClamping = CheckForClamping(originalMinCorner, cellMinCorner);
                ClampingInfo maxCornerClamping = CheckForClamping(originalMaxCorner, cellMaxCorner);

                m_cache.Resize(cellMinCorner, cellMaxCorner);
                voxelMap.Storage.ReadRange(m_cache, MyStorageDataTypeFlags.ContentAndMaterial, 0, ref cellMinCorner, ref cellMaxCorner);

                ulong filledSum = 0;

                for (var it = new Vector3I_RangeIterator(ref cellMinCorner, ref cellMaxCorner); it.IsValid(); it.MoveNext())
                {
                    var relPos   = it.Current - cellMinCorner; // get original amount
                    var original = m_cache.Content(ref relPos);

                    if (original == MyVoxelConstants.VOXEL_CONTENT_FULL) // if there is nothing to add
                    {
                        continue;
                    }

                    //if there was some claping, fill the clamp region with material
                    if ((it.Current.X == cellMinCorner.X && minCornerClamping.X) || (it.Current.X == cellMaxCorner.X && maxCornerClamping.X) ||
                        (it.Current.Y == cellMinCorner.Y && minCornerClamping.Y) || (it.Current.Y == cellMaxCorner.Y && maxCornerClamping.Y) ||
                        (it.Current.Z == cellMinCorner.Z && minCornerClamping.Z) || (it.Current.Z == cellMaxCorner.Z && maxCornerClamping.Z))
                    {
                        m_cache.Material(ref relPos, materialIdx);
                        continue;
                    }

                    Vector3D vpos;
                    MyVoxelCoordSystems.VoxelCoordToWorldPosition(voxelMap.PositionLeftBottomCorner, ref it.Current, out vpos);
                    var volume = shape.GetVolume(ref vpos);


                    if (volume <= 0f) // there is nothing to fill
                    {
                        continue;
                    }

                    m_cache.Material(ref relPos, materialIdx); // set material

                    var  toFill = (int)(volume * MyVoxelConstants.VOXEL_CONTENT_FULL);
                    long newVal = MathHelper.Clamp(original + toFill, 0, Math.Max(original, toFill));

                    m_cache.Content(ref relPos, (byte)newVal);
                    filledSum += (ulong)(newVal - original);
                }
                if (filledSum > 0)
                {
                    RemoveSmallVoxelsUsingChachedVoxels();
                    voxelMap.Storage.WriteRange(m_cache, MyStorageDataTypeFlags.ContentAndMaterial, ref cellMinCorner, ref cellMaxCorner);
                }

                retValue += filledSum;
            }

            if (retValue > 0)
            {
                OnVoxelChanged(MyVoxelBase.OperationType.Fill, voxelMap, shape);
            }

            return(retValue);
        }
        private static ClampingInfo CheckForClamping(Vector3I originalValue, Vector3I clampedValue)
        {
            ClampingInfo ret = new ClampingInfo(false, false, false);
            if (originalValue.X != clampedValue.X)
            {
                ret.X = true;
            }

            if (originalValue.Y != clampedValue.Y)
            {
                ret.Y = true;
            }
            if (originalValue.Z != clampedValue.Z)
            {
                ret.Z = true;
            }
            return ret;
        }
Beispiel #4
0
 public static void FillInShape(MyVoxelBase voxelMap, MyShape shape, byte materialIdx)
 {
     using (voxelMap.Pin())
     {
         if (!voxelMap.MarkedForClose)
         {
             Vector3I vectori;
             Vector3I maxCorner;
             Vector3I minCorner;
             ulong    num = 0UL;
             GetVoxelShapeDimensions(voxelMap, shape, out minCorner, out maxCorner, out vectori);
             minCorner = Vector3I.Max(Vector3I.One, minCorner);
             maxCorner = Vector3I.Max(minCorner, maxCorner - Vector3I.One);
             if (m_cache == null)
             {
                 m_cache = new MyStorageData(MyStorageDataTypeFlags.All);
             }
             Vector3I_RangeIterator it = new Vector3I_RangeIterator(ref Vector3I.Zero, ref vectori);
             while (true)
             {
                 Vector3I vectori2;
                 Vector3I vectori3;
                 if (!it.IsValid())
                 {
                     if (num > 0L)
                     {
                         BoundingBoxD cutOutBox = shape.GetWorldBoundaries();
                         MySandboxGame.Static.Invoke(delegate {
                             if (voxelMap.Storage != null)
                             {
                                 voxelMap.Storage.NotifyChanged(minCorner, maxCorner, MyStorageDataTypeFlags.All);
                                 NotifyVoxelChanged(MyVoxelBase.OperationType.Fill, voxelMap, ref cutOutBox);
                             }
                         }, "FillInShape Notify");
                     }
                     break;
                 }
                 GetCellCorners(ref minCorner, ref maxCorner, ref it, out vectori2, out vectori3);
                 Vector3I originalValue = vectori3;
                 voxelMap.Storage.ClampVoxelCoord(ref vectori2, 0);
                 voxelMap.Storage.ClampVoxelCoord(ref vectori3, 0);
                 ClampingInfo info  = CheckForClamping(vectori2, vectori2);
                 ClampingInfo info2 = CheckForClamping(originalValue, vectori3);
                 m_cache.Resize(vectori2, vectori3);
                 MyVoxelRequestFlags considerContent = MyVoxelRequestFlags.ConsiderContent;
                 voxelMap.Storage.ReadRange(m_cache, MyStorageDataTypeFlags.All, 0, vectori2, vectori3, ref considerContent);
                 ulong num2 = 0UL;
                 Vector3I_RangeIterator iterator2 = new Vector3I_RangeIterator(ref vectori2, ref vectori3);
                 while (true)
                 {
                     if (!iterator2.IsValid())
                     {
                         if (num2 > 0L)
                         {
                             RemoveSmallVoxelsUsingChachedVoxels();
                             voxelMap.Storage.WriteRange(m_cache, MyStorageDataTypeFlags.All, vectori2, vectori3, false, true);
                         }
                         num += num2;
                         it.MoveNext();
                         break;
                     }
                     Vector3I p    = iterator2.Current - vectori2;
                     byte     num3 = m_cache.Content(ref p);
                     if ((num3 != 0xff) || (m_cache.Material(ref p) != materialIdx))
                     {
                         if ((((iterator2.Current.X == vectori2.X) && info.X) || (((iterator2.Current.X == vectori3.X) && info2.X) || (((iterator2.Current.Y == vectori2.Y) && info.Y) || (((iterator2.Current.Y == vectori3.Y) && info2.Y) || ((iterator2.Current.Z == vectori2.Z) && info.Z))))) || ((iterator2.Current.Z == vectori3.Z) && info2.Z))
                         {
                             if (num3 != 0)
                             {
                                 m_cache.Material(ref p, materialIdx);
                             }
                         }
                         else
                         {
                             Vector3D vectord;
                             MyVoxelCoordSystems.VoxelCoordToWorldPosition(voxelMap.PositionLeftBottomCorner, ref iterator2.Current, out vectord);
                             float volume = shape.GetVolume(ref vectord);
                             if (volume > 0f)
                             {
                                 long num6 = Math.Max(num3, (int)(volume * 255f));
                                 m_cache.Content(ref p, (byte)num6);
                                 if (num6 != 0)
                                 {
                                     m_cache.Material(ref p, materialIdx);
                                 }
                                 num2 += ((ulong)num6) - num3;
                             }
                         }
                     }
                     iterator2.MoveNext();
                 }
             }
         }
     }
 }