SendNow() public method

Send packet to player (synchronous). Sends the packet off immediately. Should not be used from any thread other than this session's IoThread. Not thread-safe (for performance reason).
public SendNow ( Packet packet ) : void
packet Packet
return void
Ejemplo n.º 1
0
        /// <summary> Handles manually-placed/deleted blocks.
        /// Returns true if player's action should result in a kick. </summary>
        public bool PlaceBlock(short x, short y, short h, bool buildMode, Block type)
        {
            LastUsedBlockType = type;

            // check if player is frozen or too far away to legitimately place a block
            if (Info.IsFrozen ||
                Math.Abs(x * 32 - Position.X) > MaxRange ||
                Math.Abs(y * 32 - Position.Y) > MaxRange ||
                Math.Abs(h * 32 - Position.H) > MaxRange)
            {
                RevertBlockNow(x, y, h);
                return(false);
            }

            if (World.IsLocked)
            {
                RevertBlockNow(x, y, h);
                Message("This map is currently locked (read-only).");
                return(false);
            }

            if (CheckBlockSpam())
            {
                return(true);
            }

            // bindings
            bool requiresUpdate = (type != bindings[(byte)type] || IsPainting);

            if (!buildMode && !IsPainting)
            {
                type = Block.Air;
            }
            type = bindings[(byte)type];

            // selection handling
            if (SelectionMarksExpected > 0)
            {
                RevertBlockNow(x, y, h);
                AddSelectionMark(new Position(x, y, h), true);
                return(false);
            }

            CanPlaceResult canPlaceResult;

            if (type == Block.Stair && h > 0 && World.Map.GetBlock(x, y, h - 1) == Block.Stair)
            {
                // stair stacking
                canPlaceResult = CanPlace(x, y, h - 1, Block.DoubleStair, true);
            }
            else
            {
                // normal placement
                canPlaceResult = CanPlace(x, y, h, type, true);
            }

            // if all is well, try placing it
            switch (canPlaceResult)
            {
            case CanPlaceResult.Allowed:
                BlockUpdate blockUpdate;
                if (type == Block.Stair && h > 0 && World.Map.GetBlock(x, y, h - 1) == Block.Stair)
                {
                    // handle stair stacking
                    blockUpdate = new BlockUpdate(this, x, y, h - 1, Block.DoubleStair);
                    if (!World.FireChangedBlockEvent(ref blockUpdate))
                    {
                        RevertBlockNow(x, y, h);
                        return(false);
                    }
                    Info.ProcessBlockPlaced((byte)Block.DoubleStair);
                    World.Map.QueueUpdate(blockUpdate);
                    Server.RaisePlayerPlacedBlockEvent(this, x, y, (short)(h - 1), Block.Stair, Block.DoubleStair, true);
                    Session.SendNow(PacketWriter.MakeSetBlock(x, y, h - 1, Block.DoubleStair));
                    RevertBlockNow(x, y, h);
                    break;
                }
                else
                {
                    // handle normal blocks
                    blockUpdate = new BlockUpdate(this, x, y, h, type);
                    if (!World.FireChangedBlockEvent(ref blockUpdate))
                    {
                        RevertBlockNow(x, y, h);
                        return(false);
                    }
                    Info.ProcessBlockPlaced((byte)type);
                    Block old = World.Map.GetBlock(x, y, h);
                    World.Map.QueueUpdate(blockUpdate);
                    Server.RaisePlayerPlacedBlockEvent(this, x, y, h, old, type, true);
                    if (requiresUpdate || RelayAllUpdates)
                    {
                        Session.SendNow(PacketWriter.MakeSetBlock(x, y, h, type));
                    }
                }
                break;

            case CanPlaceResult.BlocktypeDenied:
                Message("&WYou are not permitted to affect this block type.");
                RevertBlockNow(x, y, h);
                break;

            case CanPlaceResult.RankDenied:
                Message("&WYour rank is not allowed to build.");
                RevertBlockNow(x, y, h);
                break;

            case CanPlaceResult.WorldDenied:
                switch (World.BuildSecurity.CheckDetailed(Info))
                {
                case SecurityCheckResult.RankTooLow:
                case SecurityCheckResult.RankTooHigh:
                    Message("&WYour rank is not allowed to build in this world.");
                    break;

                case SecurityCheckResult.BlackListed:
                    Message("&WYou are not allowed to build in this world.");
                    break;
                }
                RevertBlockNow(x, y, h);
                break;

            case CanPlaceResult.ZoneDenied:
                Zone deniedZone = World.Map.FindDeniedZone(x, y, h, this);
                if (deniedZone != null)
                {
                    Message("&WYou are not allowed to build in zone \"{0}\".", deniedZone.Name);
                }
                else
                {
                    Message("&WYou are not allowed to build here.");
                }
                RevertBlockNow(x, y, h);
                break;

            case CanPlaceResult.PluginDenied:
                RevertBlockNow(x, y, h);
                break;

                //case CanPlaceResult.PluginDeniedNoUpdate:
                //    break;
            }
            return(false);
        }
Ejemplo n.º 2
0
        // Handles building/deleting by the player
        public void SetTile(short x, short y, short h, bool buildMode, Block type)
        {
            if (CheckBlockSpam())
            {
                return;
            }

            if (world.lockDown)
            {
                session.SendNow(PacketWriter.MakeSetBlock(x, y, h, world.map.GetBlock(x, y, h)));
                Message("Map is temporarily locked. Please wait.");
                return;
            }

            // check if player is too far away to legitimately place a block
            if (Math.Abs(x * 32 - pos.x) > maxRange ||
                Math.Abs(y * 32 - pos.y) > maxRange ||
                Math.Abs(h * 32 - pos.h) > maxRange)
            {
                session.SendNow(PacketWriter.MakeSetBlock(x, y, h, world.map.GetBlock(x, y, h)));
                return;
            }

            foreach (Zone zone in world.map.zones)
            {
                if (zone.Contains(x, y, h))
                {
                    if (!zone.CanBuild(this))
                    {
                        session.SendNow(PacketWriter.MakeSetBlock(x, y, h, world.map.GetBlock(x, y, h)));
                        Message("You are not allowed to build in this zone (" + zone.name + ").");
                        return;
                    }
                }
            }

            // action block handling
            if (marksExpected > 0)
            {
                session.SendNow(PacketWriter.MakeSetBlock(x, y, h, world.map.GetBlock(x, y, h)));
                marks.Push(new Position(x, y, h));
                markCount++;
                if (markCount >= marksExpected)
                {
                    marksExpected = 0;
                    selectionCallback(this, marks.ToArray(), tag);
                }
                else
                {
                    Message(String.Format("Block #{0} marked at ({1},{2},{3}). Place mark #{4}.",
                                          markCount, x, y, h, markCount + 1));
                }
                return;
            }

            bool can    = true;
            bool update = true;

            if (type == Block.Air)
            {
                buildMode = false;
            }

            // handle special placement modes
            switch (mode)
            {
            case BlockPlacementMode.Grass:
                if (type == Block.Dirt)
                {
                    type = Block.Grass;
                }
                break;

            case BlockPlacementMode.Lava:
                if (type == Block.Orange || type == Block.Red)
                {
                    type = Block.Lava;
                }
                break;

            case BlockPlacementMode.Solid:
                if (type == Block.Stone)
                {
                    type = Block.Admincrete;
                }
                break;

            case BlockPlacementMode.Water:
                if (type == Block.Aqua || type == Block.Cyan || type == Block.Blue)
                {
                    type = Block.Water;
                }
                break;

            default:
                update = false;
                break;
            }

            // check if the user has the permission to BUILD the block
            if (buildMode || replaceMode)
            {
                if (type == Block.Lava || type == Block.StillLava)
                {
                    can = Can(Permissions.PlaceLava);
                }
                else if (type == Block.Water || type == Block.StillWater)
                {
                    can = Can(Permissions.PlaceWater);
                }
                else if (type == Block.Admincrete)
                {
                    can = Can(Permissions.PlaceAdmincrete);
                }
                else
                {
                    can = Can(Permissions.Build);
                }
            }
            else
            {
                type = Block.Air;
            }

            // check that the user has permission to DELETE/REPLACE the block
            if (world.map.GetBlock(x, y, h) == (byte)Block.Admincrete)
            {
                can &= Can(Permissions.DeleteAdmincrete);
            }
            else if (world.map.GetBlock(x, y, h) != (byte)Block.Air)
            {
                can &= Can(Permissions.Delete);
            }

            // if all is well, try placing it
            if (can)
            {
                if (type == Block.Stair && h > 0 && world.map.GetBlock(x, y, h - 1) == (byte)Block.Stair)
                {
                    session.SendNow(PacketWriter.MakeSetBlock(x, y, h - 1, (byte)Block.DoubleStair));
                    session.SendNow(PacketWriter.MakeSetBlock(x, y, h, (byte)Block.Air));
                    world.map.QueueUpdate(new BlockUpdate(this, x, y, h - 1, (byte)Block.DoubleStair));
                }
                else
                {
                    world.map.QueueUpdate(new BlockUpdate(this, x, y, h, (byte)type));
                    if (update || replaceMode)
                    {
                        session.SendNow(PacketWriter.MakeSetBlock(x, y, h, (byte)type));
                    }
                }
            }
            else
            {
                Message(Color.Red, "You are not permitted to do that.");
                session.SendNow(PacketWriter.MakeSetBlock(x, y, h, world.map.GetBlock(x, y, h)));
            }
        }