コード例 #1
0
    // TODO: Pseudo RNG so the client can predict these.
    #region Hitscan effects

    private void FireEffects(EntityCoordinates fromCoordinates, float distance, Angle angle, HitscanPrototype hitscan, EntityUid?hitEntity = null)
    {
        // Lord
        // Forgive me for the shitcode I am about to do
        // Effects tempt me not
        var sprites = new List <(EntityCoordinates coordinates, Angle angle, SpriteSpecifier sprite, float scale)>();

        // We'll get the effects relative to the grid / map of the firer
        if (distance >= 1f)
        {
            if (hitscan.MuzzleFlash != null)
            {
                sprites.Add((fromCoordinates.Offset(angle.ToVec().Normalized / 2), angle, hitscan.MuzzleFlash, 1f));
            }

            if (hitscan.TravelFlash != null)
            {
                sprites.Add((fromCoordinates.Offset(angle.ToVec() * (distance + 0.5f) / 2), angle, hitscan.TravelFlash, distance - 1.5f));
            }
        }

        if (hitscan.ImpactFlash != null)
        {
            sprites.Add((fromCoordinates.Offset(angle.ToVec() * distance), angle.FlipPositive(), hitscan.ImpactFlash, 1f));
        }

        if (sprites.Count > 0)
        {
            RaiseNetworkEvent(new HitscanEvent()
            {
                Sprites = sprites,
            }, Filter.Pvs(fromCoordinates, entityMan: EntityManager));
        }
    }
コード例 #2
0
        private void PlaceAt(IMapGrid mapGrid, EntityCoordinates location, ushort tileId, float offset = 0)
        {
            var variant = _random.Pick(((ContentTileDefinition)_tileDefinitionManager[tileId]).PlacementVariants);

            mapGrid.SetTile(location.Offset(new Vector2(offset, offset)), new Tile(tileId, 0, variant));
            SoundSystem.Play(Filter.Pvs(location), _placeTileSound.GetSound(), location, AudioHelpers.WithVariation(0.125f));
        }
コード例 #3
0
        public override void AlignPlacementMode(ScreenCoordinates mouseScreen)
        {
            MouseCoords = ScreenToCursorGrid(mouseScreen);
            CurrentTile = GetTileRef(MouseCoords);

            if (pManager.CurrentPermission !.IsTile)
            {
                return;
            }

            var tileCoordinates = new EntityCoordinates(MouseCoords.EntityId, CurrentTile.GridIndices);

            var offsets = new Vector2[]
            {
                (0f, 0.5f),
                (0.5f, 0f),
                (0, -0.5f),
                (-0.5f, 0f)
            };

            var closestNode = offsets
                              .Select(o => tileCoordinates.Offset(o))
                              .OrderBy(node => node.TryDistance(pManager.EntityManager, MouseCoords, out var distance) ? distance : (float?)null)
                              .First();

            MouseCoords = closestNode;
        }
コード例 #4
0
        public void FireEffects(EntityUid user, float distance, Angle angle, EntityUid?hitEntity = null)
        {
            var effectSystem = EntitySystem.Get <EffectSystem>();

            _startTime = _gameTiming.CurTime;
            _deathTime = _startTime + TimeSpan.FromSeconds(1);

            var mapManager = IoCManager.Resolve <IMapManager>();

            // We'll get the effects relative to the grid / map of the firer
            var gridOrMap = _entMan.GetComponent <TransformComponent>(user).GridID == GridId.Invalid ? mapManager.GetMapEntityId(_entMan.GetComponent <TransformComponent>(user).MapID) :
                            mapManager.GetGrid(_entMan.GetComponent <TransformComponent>(user).GridID).GridEntityId;

            var parentXform = _entMan.GetComponent <TransformComponent>(gridOrMap);

            var localCoordinates = new EntityCoordinates(gridOrMap, parentXform.InvWorldMatrix.Transform(_entMan.GetComponent <TransformComponent>(user).WorldPosition));
            var localAngle       = angle - parentXform.WorldRotation;

            var afterEffect = AfterEffects(localCoordinates, localAngle, distance, 1.0f);

            if (afterEffect != null)
            {
                effectSystem.CreateParticle(afterEffect);
            }

            // if we're too close we'll stop the impact and muzzle / impact sprites from clipping
            if (distance > 1.0f)
            {
                var impactEffect = ImpactFlash(distance, localAngle);
                if (impactEffect != null)
                {
                    effectSystem.CreateParticle(impactEffect);
                }

                var muzzleEffect = MuzzleFlash(localCoordinates, localAngle);
                if (muzzleEffect != null)
                {
                    effectSystem.CreateParticle(muzzleEffect);
                }
            }

            if (hitEntity != null && _soundHitWall != null)
            {
                // TODO: No wall component so ?
                var offset      = localAngle.ToVec().Normalized / 2;
                var coordinates = localCoordinates.Offset(offset);
                SoundSystem.Play(Filter.Pvs(coordinates), _soundHitWall.GetSound(), coordinates);
            }

            Owner.SpawnTimer((int)_deathTime.TotalMilliseconds, () =>
            {
                if (!_entMan.Deleted(Owner))
                {
                    _entMan.DeleteEntity(Owner);
                }
            });
        }
コード例 #5
0
        /// <summary>
        ///     Gets tiles in random directions from the given one.
        /// </summary>
        /// <returns>An enumerable of the adjacent tiles.</returns>
        public static IEnumerable <TileRef> AdjacentTilesRandom(this EntityCoordinates coordinates, bool ignoreSpace = false)
        {
            foreach (var direction in RandomDirections())
            {
                var adjacent = coordinates.Offset(direction).GetTileRef();

                if (adjacent == null)
                {
                    continue;
                }

                if (ignoreSpace && adjacent.Value.Tile.IsEmpty)
                {
                    continue;
                }

                yield return(adjacent.Value);
            }
        }
コード例 #6
0
        private EffectSystemMessage AfterEffects(EntityCoordinates origin, Angle angle, float distance, float offset = 0.0f)
        {
            var midPointOffset = angle.ToVec() * distance / 2;
            var message        = new EffectSystemMessage
            {
                EffectSprite = _spriteName,
                Born         = _startTime,
                DeathTime    = _deathTime,
                Size         = new Vector2(distance - offset, 1f),
                Coordinates  = origin.Offset(midPointOffset),
                //Rotated from east facing
                Rotation   = (float)angle.Theta,
                Color      = Vector4.Multiply(new Vector4(255, 255, 255, 750), ColorModifier),
                ColorDelta = new Vector4(0, 0, 0, -1500f),

                Shaded = false
            };

            return(message);
        }
コード例 #7
0
        public override void AlignPlacementMode(ScreenCoordinates mouseScreen)
        {
            MouseCoords = ScreenToCursorGrid(mouseScreen);
            CurrentTile = GetTileRef(MouseCoords);

            if (pManager.CurrentPermission !.IsTile)
            {
                return;
            }

            var tileCoordinates = new EntityCoordinates(MouseCoords.EntityId, CurrentTile.GridIndices);

            Vector2 offset;

            switch (pManager.Direction)
            {
            case Direction.North:
                offset = new Vector2(0.5f, 1f);
                break;

            case Direction.South:
                offset = new Vector2(0.5f, 0f);
                break;

            case Direction.East:
                offset = new Vector2(1f, 0.5f);
                break;

            case Direction.West:
                offset = new Vector2(0f, 0.5f);
                break;

            default:
                return;
            }

            tileCoordinates = tileCoordinates.Offset(offset);
            MouseCoords     = tileCoordinates;
        }
コード例 #8
0
        private EffectSystemMessage?MuzzleFlash(EntityCoordinates grid, Angle angle)
        {
            if (_muzzleFlash == null)
            {
                return(null);
            }

            var offset = angle.ToVec().Normalized / 2;

            var message = new EffectSystemMessage
            {
                EffectSprite = _muzzleFlash,
                Born         = _startTime,
                DeathTime    = _deathTime,
                Coordinates  = grid.Offset(offset),
                //Rotated from east facing
                Rotation   = (float)angle.Theta,
                Color      = Vector4.Multiply(new Vector4(255, 255, 255, 750), ColorModifier),
                ColorDelta = new Vector4(0, 0, 0, -1500f),
                Shaded     = false
            };

            return(message);
        }
コード例 #9
0
 public static EntityCoordinates Offset(this EntityCoordinates coordinates, Direction direction)
 {
     return(coordinates.Offset(direction.ToVec()));
 }
コード例 #10
0
 private void PlaceAt(IMapGrid mapGrid, EntityCoordinates location, ushort tileId, float offset = 0)
 {
     mapGrid.SetTile(location.Offset(new Vector2(offset, offset)), new Tile(tileId));
     EntitySystem.Get <AudioSystem>().PlayAtCoords("/Audio/Items/genhit.ogg", location, AudioHelpers.WithVariation(0.125f));
 }
コード例 #11
0
 private void PlaceAt(IMapGrid mapGrid, EntityCoordinates location, ushort tileId, float offset = 0)
 {
     mapGrid.SetTile(location.Offset(new Vector2(offset, offset)), new Tile(tileId));
     SoundSystem.Play(Filter.Pvs(location), _placeTileSound.GetSound(), location, AudioHelpers.WithVariation(0.125f));
 }
コード例 #12
0
            public void Update(float frameTime)
            {
                Age += TimeSpan.FromSeconds(frameTime);
                if (Age >= Deathtime)
                {
                    return;
                }

                Velocity           += Acceleration * frameTime;
                RadialVelocity     += RadialAcceleration * frameTime;
                TangentialVelocity += TangentialAcceleration * frameTime;

                var deltaPosition = new Vector2(0f, 0f);

                //If we have an emitter we can do special effects around that emitter position
                if (_mapManager.GridExists(EmitterCoordinates.GetGridId(_entityManager)))
                {
                    //Calculate delta p due to radial velocity
                    var positionRelativeToEmitter =
                        Coordinates.ToMapPos(_entityManager) - EmitterCoordinates.ToMapPos(_entityManager);
                    var deltaRadial = RadialVelocity * frameTime;
                    deltaPosition = positionRelativeToEmitter * (deltaRadial / positionRelativeToEmitter.Length);

                    //Calculate delta p due to tangential velocity
                    var radius = positionRelativeToEmitter.Length;
                    if (radius > 0)
                    {
                        var theta = (float)Math.Atan2(positionRelativeToEmitter.Y, positionRelativeToEmitter.X);
                        theta         += TangentialVelocity * frameTime;
                        deltaPosition += new Vector2(radius * (float)Math.Cos(theta), radius * (float)Math.Sin(theta))
                                         - positionRelativeToEmitter;
                    }
                }

                //Calculate new position from our velocity as well as possible rotation/movement around emitter
                deltaPosition += Velocity * frameTime;
                Coordinates    = Coordinates.Offset(deltaPosition);

                //Finish calculating new rotation, size, color
                Rotation += RotationRate * frameTime;
                Size     += SizeDelta * frameTime;
                Color    += ColorDelta * frameTime;

                if (RsiState == null)
                {
                    return;
                }

                // Calculate RSI animations.
                var delayCount = RsiState.DelayCount;

                if (delayCount > 0 && (AnimationLoops || AnimationIndex < delayCount - 1))
                {
                    AnimationTime += frameTime;
                    while (RsiState.GetDelay(AnimationIndex) < AnimationTime)
                    {
                        var delay = RsiState.GetDelay(AnimationIndex);
                        AnimationIndex += 1;
                        AnimationTime  -= delay;
                        if (AnimationIndex == delayCount)
                        {
                            if (AnimationLoops)
                            {
                                AnimationIndex = 0;
                            }
                            else
                            {
                                break;
                            }
                        }

                        EffectSprite = RsiState.GetFrame(RSI.State.Direction.South, AnimationIndex);
                    }
                }
            }
コード例 #13
0
 private void PlaceAt(IMapGrid mapGrid, EntityCoordinates location, ushort tileId, float offset = 0)
 {
     mapGrid.SetTile(location.Offset(new Vector2(offset, offset)), new Robust.Shared.Map.Tile(tileId));
     SoundSystem.Play(Filter.Pvs(location), "/Audio/Items/genhit.ogg", location, AudioHelpers.WithVariation(0.125f));
 }