public void GetBlocksInsideSphereBrute(MyCubeGrid grid, Vector3I center, ref BoundingSphereD sphere, bool sorted) { if (grid.PositionComp == null) { return; } if (sorted) { _slimsSortedList.Clear(); } else { _slimsSet.Clear(); } var matrixNormalizedInv = grid.PositionComp.WorldMatrixNormalizedInv; Vector3D result; Vector3D.Transform(ref sphere.Center, ref matrixNormalizedInv, out result); var localSphere = new BoundingSphere(result, (float)sphere.Radius); foreach (IMySlimBlock cube in grid.CubeBlocks) { if (new BoundingBox(cube.Min * grid.GridSize - grid.GridSizeHalf, cube.Max * grid.GridSize + grid.GridSizeHalf).Intersects(localSphere)) { var radiatedBlock = new RadiatedBlock { Center = center, Slim = cube, Position = cube.Position, }; if (sorted) { _slimsSortedList.Add(radiatedBlock); } else { _slimsSet.Add(cube); } } } if (sorted) { _slimsSortedList.Sort((x, y) => Vector3I.DistanceManhattan(x.Position, x.Slim.Position).CompareTo(Vector3I.DistanceManhattan(y.Position, y.Slim.Position))); } }
/// <summary> /// Called when a new block is placed on same grid as this pocket gear. Used to enable protection. /// </summary> /// <param name="slimBlock">The blocks that is added.</param> private void OnBlockAdded(IMySlimBlock slimBlock) { if (Mod.Static.DamageHandler == null) { return; } var position = slimBlock.Position; var distance = Vector3I.DistanceManhattan(position, Stator.Position); if (distance <= Mod.Static.Settings.ProtectionRadius) { _neighbors.Add(slimBlock); if (IsProtected) { Mod.Static.DamageHandler.EnableProtection(slimBlock); } } }
/// <summary> /// Called when a block is removed from same grid as this pocket gear. Used to disable protection. /// </summary> /// <param name="slimBlock"></param> private void OnBlockRemoved(IMySlimBlock slimBlock) { if (Mod.Static.DamageHandler == null) { return; } if (!_neighbors.Contains(slimBlock)) { return; } var position = slimBlock.Position; var distance = Vector3I.DistanceManhattan(position, Stator.Position); if (distance <= Mod.Static.Settings.ProtectionRadius) { _neighbors.Remove(slimBlock); Mod.Static.DamageHandler.DisableProtection(slimBlock); } }
private static long?castTargetingRay(Dictionary <IMyEntity, ushort> targetTypeDictionary, SmartTurret turret) { IMyEntity turretEntity = turret.Entity; if (turretEntity == null) { return(null); } IMySlimBlock turretSlimBlock = (turretEntity as IMyCubeBlock).SlimBlock; IMyCubeGrid turretCubeGrid = turretSlimBlock.CubeGrid; Vector3D turretLocation = getTurretLocation(turretEntity); List <IMyCubeGrid> grids = new List <IMyCubeGrid>(); List <IMySlimBlock> turretGridBlockList = new List <IMySlimBlock>(); List <IMySlimBlock> targetGridBlockList = new List <IMySlimBlock>(); try { turretCubeGrid.GetBlocks(turretGridBlockList, (x) => { return(x != turretSlimBlock); }); } catch { //Harmless Enumeration error, stop targeting. return(null); } foreach (KeyValuePair <IMyEntity, ushort> pair in targetTypeDictionary) { grids.Clear(); targetGridBlockList.Clear(); IMySlimBlock targetSlimBlock = null; IMyEntity target = pair.Key; bool isTargetValid = true; IMyCubeGrid targetCubeGrid = null; Vector3D targetLocation = target.GetPosition(); LineD line = new LineD(turretLocation, targetLocation); BoundingSphereD entityCollectionZone = new BoundingSphereD(turretLocation + (turretLocation - targetLocation) / 2, Vector3D.Distance(turretLocation, targetLocation) + 1000); List <IMyEntity> entities = MyAPIGateway.Entities.GetEntitiesInSphere(ref entityCollectionZone); //Block specific setup if (target is IMyCubeBlock) { targetSlimBlock = (target as IMyCubeBlock).SlimBlock; targetCubeGrid = targetSlimBlock.CubeGrid; try { targetCubeGrid.GetBlocks(targetGridBlockList, (x) => { return(x != targetSlimBlock); }); } catch { //Harmless Enumeration error, stop targeting. return(null); } } //More setup and check voxels foreach (IMyEntity entity in entities) { if (entity is IMyCubeGrid) { IMyCubeGrid grid = entity as IMyCubeGrid; if (grid != turretCubeGrid && grid != targetCubeGrid) { grids.Add(grid); } } else if (entity is MyVoxelBase) { Vector3D?output; if ((entity as MyVoxelBase).GetIntersectionWithLine(ref line, out output)) { //log("Target: " + target.GetType().ToString() + " Failed because of intersecting voxel"); isTargetValid = false; break; } } } if (!isTargetValid) { continue; } //Relation of intersecting grids foreach (IMyCubeGrid grid in grids) { if (grid.WorldAABB.Intersects(ref line) == true) { List <IMySlimBlock> currentGridBlocks = new List <IMySlimBlock>(); try { grid.GetBlocks(currentGridBlocks); } catch { //Harmless Enumeration error, stop targeting. return(null); } MyRelationsBetweenPlayerAndBlock relation = MyRelationsBetweenPlayerAndBlock.NoOwnership; if (grid.BigOwners.Count > 0) { relation = turretSlimBlock.FatBlock.GetUserRelationToOwner(grid.BigOwners[0]); } bool throughFriendliesState = pair.Value == 35 ? false : turret.throughFriendliesStateDictionary[pair.Value]; bool throughNeutralsState = pair.Value == 35 ? false : turret.throughNeutralsStateDictionary[pair.Value]; bool throughHostilesState = pair.Value == 35 ? false : turret.throughHostilesStateDictionary[pair.Value]; if ((!throughHostilesState && relation == MyRelationsBetweenPlayerAndBlock.Enemies) || (!throughNeutralsState && (relation == MyRelationsBetweenPlayerAndBlock.Neutral || relation == MyRelationsBetweenPlayerAndBlock.NoOwnership)) || (!throughFriendliesState && (relation == MyRelationsBetweenPlayerAndBlock.Owner || relation == MyRelationsBetweenPlayerAndBlock.FactionShare))) { foreach (IMySlimBlock slimBlock in currentGridBlocks) { BoundingBoxD collisionBox; slimBlock.GetWorldBoundingBox(out collisionBox, false); //Vector3D boxCenter = collisionBox.Center; /*float azimuth; * float elevation; * getAzimuthAndElevationRelative(collisionBox.Center - turretLocation, out azimuth, out elevation); * * float tollerence = (float)(Math.Tanh(collisionBox.Size.LengthSquared() / Vector3D.DistanceSquared(boxCenter, turretLocation)) / 2 * 0.0174533); * * if (azimuth < tollerence && azimuth > -tollerence && elevation < tollerence && elevation > -tollerence) * {*/ if (collisionBox.Intersects(ref line) == true) { slimBlock.GetWorldBoundingBox(out collisionBox, true); if (collisionBox.Intersects(ref line) == true) { //log("Target: " + target.GetType().ToString() + " Failed because of intersecting other grid"); isTargetValid = false; break; } } //} } } } } if (!isTargetValid) { continue; } //If intersecting turrets grid foreach (IMySlimBlock slimBlock in turretGridBlockList) { BoundingBoxD collisionBox; slimBlock.GetWorldBoundingBox(out collisionBox, false); //Vector3D boxCenter = collisionBox.Center; /*float azimuth; * float elevation; * getAzimuthAndElevationRelative(collisionBox.Center - turretLocation, out azimuth, out elevation); * * float tollerence = (float)(Math.Tanh(collisionBox.Size.LengthSquared() / Vector3D.DistanceSquared(boxCenter, turretLocation)) / 2 * 0.0174533); * * if (azimuth < tollerence && azimuth > -tollerence && elevation < tollerence && elevation > -tollerence) * {*/ if (collisionBox.Intersects(ref line) == true) { slimBlock.GetWorldBoundingBox(out collisionBox, true); if (collisionBox.Intersects(ref line) == true) { //log("Target: " + target.GetType().ToString() + " Failed because of intersecting own grid"); isTargetValid = false; break; } } //} } if (!isTargetValid) { continue; } //If intersecting targets grid and outside of manhatten distance if (targetSlimBlock != null) { float obstacleToleranceState = pair.Value == 35 ? 3 : turret.obstacleToleranceStateDictionary[pair.Value]; if (obstacleToleranceState < 31) { foreach (IMySlimBlock slimBlock in targetGridBlockList) { BoundingBoxD collisionBox; slimBlock.GetWorldBoundingBox(out collisionBox, false); //Vector3D boxCenter = collisionBox.Center; /*float azimuth; * float elevation; * getAzimuthAndElevationRelative(collisionBox.Center - turretLocation, out azimuth, out elevation); * * float tollerence = (float)(Math.Tanh(collisionBox.Size.LengthSquared() / Vector3D.DistanceSquared(boxCenter, turretLocation)) / 2 * 0.0174533); * * if (azimuth < tollerence && azimuth > -tollerence && elevation < tollerence && elevation > -tollerence) * {*/ if (collisionBox.Intersects(ref line) == true) { slimBlock.GetWorldBoundingBox(out collisionBox, true); if (collisionBox.Intersects(ref line) == true) { if (Vector3I.DistanceManhattan(slimBlock.Position, targetSlimBlock.Position) > obstacleToleranceState) { //log("Target: " + target.GetType().ToString() + " Failed because of intersecting target grid outside of manhattan"); isTargetValid = false; break; } } } //} } } } if (!isTargetValid) { continue; } //Target Passed! return(target.EntityId); } //All targets failed return(null); }
public void GetBlocksInsideSphere(MyCubeGrid grid, Dictionary <Vector3I, IMySlimBlock> cubes, ref BoundingSphereD sphere, bool sorted, Vector3I center, bool checkTriangles = false) { if (grid.PositionComp == null) { return; } if (sorted) { _slimsSortedList.Clear(); } else { _slimsSet.Clear(); } var matrixNormalizedInv = grid.PositionComp.WorldMatrixNormalizedInv; Vector3D result; Vector3D.Transform(ref sphere.Center, ref matrixNormalizedInv, out result); var localSphere = new BoundingSphere(result, (float)sphere.Radius); var fromSphere2 = BoundingBox.CreateFromSphere(localSphere); var min = (Vector3D)fromSphere2.Min; var max = (Vector3D)fromSphere2.Max; var vector3I1 = new Vector3I((int)Math.Round(min.X * grid.GridSizeR), (int)Math.Round(min.Y * grid.GridSizeR), (int)Math.Round(min.Z * grid.GridSizeR)); var vector3I2 = new Vector3I((int)Math.Round(max.X * grid.GridSizeR), (int)Math.Round(max.Y * grid.GridSizeR), (int)Math.Round(max.Z * grid.GridSizeR)); var start = Vector3I.Min(vector3I1, vector3I2); var end = Vector3I.Max(vector3I1, vector3I2); if ((end - start).Volume() < cubes.Count) { var vector3IRangeIterator = new Vector3I_RangeIterator(ref start, ref end); var next = vector3IRangeIterator.Current; while (vector3IRangeIterator.IsValid()) { IMySlimBlock cube; if (cubes.TryGetValue(next, out cube)) { if (new BoundingBox(cube.Min * grid.GridSize - grid.GridSizeHalf, cube.Max * grid.GridSize + grid.GridSizeHalf).Intersects(localSphere)) { var radiatedBlock = new RadiatedBlock { Center = center, Slim = cube, Position = cube.Position, }; if (sorted) { _slimsSortedList.Add(radiatedBlock); } else { _slimsSet.Add(cube); } } } vector3IRangeIterator.GetNext(out next); } } else { foreach (var cube in cubes.Values) { if (new BoundingBox(cube.Min * grid.GridSize - grid.GridSizeHalf, cube.Max * grid.GridSize + grid.GridSizeHalf).Intersects(localSphere)) { var radiatedBlock = new RadiatedBlock { Center = center, Slim = cube, Position = cube.Position, }; if (sorted) { _slimsSortedList.Add(radiatedBlock); } else { _slimsSet.Add(cube); } } } } if (sorted) { _slimsSortedList.Sort((x, y) => Vector3I.DistanceManhattan(x.Position, x.Slim.Position).CompareTo(Vector3I.DistanceManhattan(y.Position, y.Slim.Position))); } }