public void LoadFromCustomModel(CustomModel model)
 {
     // convert to pixel units
     this.nameY           = model.nameY * 16.0f;
     this.eyeY            = model.eyeY * 16.0f;
     this.collisionBounds = new Vec3F32 {
         X = model.collisionBounds.X * 16.0f,
         Y = model.collisionBounds.Y * 16.0f,
         Z = model.collisionBounds.Z * 16.0f,
     };
     this.pickingBoundsMin = new Vec3F32 {
         X = model.pickingBoundsMin.X * 16.0f,
         Y = model.pickingBoundsMin.Y * 16.0f,
         Z = model.pickingBoundsMin.Z * 16.0f,
     };
     this.pickingBoundsMax = new Vec3F32 {
         X = model.pickingBoundsMax.X * 16.0f,
         Y = model.pickingBoundsMax.Y * 16.0f,
         Z = model.pickingBoundsMax.Z * 16.0f,
     };
     this.bobbing        = model.bobbing;
     this.pushes         = model.pushes;
     this.usesHumanSkin  = model.usesHumanSkin;
     this.calcHumanAnims = model.calcHumanAnims;
 }
示例#2
0
        public static AABB CalcAABB(Entity entity)
        {
            string model = GetRawModel(entity.Model);

            AABB    bb;
            BlockID raw;

            if (BlockID.TryParse(model, out raw) && raw <= Block.MaxRaw)
            {
                BlockID block = Block.FromRaw(raw);
                bb = Block.BlockAABB(block, entity.Level);
                bb = bb.Offset(-16, 0, -16); // centre around [-16, 16] instead of [0, 32]
            }
            else
            {
                bb = AABB.Make(new Vec3S32(0, 0, 0), Get(model).BaseSize);
            }
            bb = bb.Expand(-1); // adjust the model AABB inwards slightly

            Vec3F32 scale = CalcScale(entity);
            // always limit max scale for collisions performance
            float max = DefaultMaxScale(model);

            scale.X = Math.Min(scale.X, max);
            scale.Y = Math.Min(scale.Y, max);
            scale.Z = Math.Min(scale.Z, max);

            bb.Min.X = (int)(bb.Min.X * scale.X); bb.Max.X = (int)(bb.Max.X * scale.X);
            bb.Min.Y = (int)(bb.Min.Y * scale.Y); bb.Max.Y = (int)(bb.Max.Y * scale.Y);
            bb.Min.Z = (int)(bb.Min.Z * scale.Z); bb.Max.Z = (int)(bb.Max.Z * scale.Z);

            return(bb);
        }
示例#3
0
        static bool MoveTowards(PlayerBot bot, Player p, Metadata meta)
        {
            if (p == null)
            {
                return(false);
            }
            int dist = (int)(0.875 * 32);

            int dx = p.Pos.X - bot.Pos.X, dy = p.Pos.Y - bot.Pos.Y, dz = p.Pos.Z - bot.Pos.Z;

            bot.TargetPos = p.Pos;
            bot.movement  = true;

            Vec3F32 dir = new Vec3F32(dx, dy, dz);

            dir = Vec3F32.Normalise(dir);
            Orientation rot = bot.Rot;

            DirUtils.GetYawPitch(dir, out rot.RotY, out rot.HeadX);


            MobAI.SetDirectionalSpeeds(bot);

            dx = Math.Abs(dx); dy = Math.Abs(dy); dz = Math.Abs(dz);
            if (InRange(p, bot, dist))
            {
                p.Message("%cInfect");
            }

            bot.Rot = rot;


            return(dx <= 8 && dy <= 16 && dz <= 8);
        }
示例#4
0
        static bool MoveTowards(PlayerBot bot, Player p, Metadata meta)
        {
            if (p == null)
            {
                return(false);
            }

            int dx = p.Pos.X - bot.Pos.X, dy = p.Pos.Y - bot.Pos.Y, dz = p.Pos.Z - bot.Pos.Z;

            bot.TargetPos = p.Pos;
            bot.movement  = true;

            Vec3F32 dir = new Vec3F32(dx, dy, dz);

            dir = Vec3F32.Normalise(dir);
            Orientation rot = bot.Rot;

            DirUtils.GetYawPitch(dir, out rot.RotY, out rot.HeadX);

            MobAI.SetDirectionalSpeeds(bot);

            p.Message("I am facing: %b" + MobAI.CalculateCardinal(bot));

            p.Message("sp " + bot.movementSpeed);

            //p.Message("The block in front of me is: %b");

            dx = Math.Abs(dx); dy = Math.Abs(dy); dz = Math.Abs(dz);

            bot.Rot = rot;

            return(dx <= 8 && dy <= 16 && dz <= 8);
        }
        void Step(PlayerBot bot)
        {
            bot.TargetPos = bot.Pos;
            bot.movement  = true;
            Vec3F32 dir = DirUtils.GetDirVector(bot.Rot.RotY, 0);

            bot.TargetPos.X = bot.Pos.X + (int)(dir.X * bot.movementSpeed);
            bot.TargetPos.Z = bot.Pos.Z + (int)(dir.Z * bot.movementSpeed);
        }
示例#6
0
        static bool MoveTowards(PlayerBot bot, Player p, Metadata meta)
        {
            if (p == null)
            {
                return(false);
            }

            int dx = p.Pos.X - bot.Pos.X, dy = p.Pos.Y - bot.Pos.Y, dz = p.Pos.Z - bot.Pos.Z;

            bot.TargetPos = p.Pos;
            bot.movement  = true;

            Vec3F32 dir = new Vec3F32(dx, dy, dz);

            dir = Vec3F32.Normalise(dir);
            Orientation rot = bot.Rot;

            DirUtils.GetYawPitch(dir, out rot.RotY, out rot.HeadX);

            MobAI.SetDirectionalSpeeds(bot);

            dx = Math.Abs(dx); dy = Math.Abs(dy); dz = Math.Abs(dz);

            if (bot.Model == "creeper")
            {
                if (dx < (3 * 32) && dz < (3 * 32))
                {
                    if (meta.explodeTime == 0)
                    {
                        meta.explodeTime = 10;
                    }
                }
                else
                {
                    meta.explodeTime = 0;
                }
            }

            else
            {
                if ((dx <= 8 && dy <= 16 && dz <= 8))
                {
                    HitPlayer(bot, p, rot);
                }
            }

            bot.Rot = rot;


            return(dx <= 8 && dy <= 16 && dz <= 8);
        }
示例#7
0
        /// <summary>
        /// Face bot towards target position.
        /// </summary>
        /// <param name="bot"></param>

        public static void FaceTowards(PlayerBot bot)
        {
            int dstHeight = ModelInfo.CalcEyeHeight(bot);

            int     dx = (bot.TargetPos.X) - bot.Pos.X, dy = bot.Rot.RotY, dz = (bot.TargetPos.Z) - bot.Pos.Z;
            Vec3F32 dir = new Vec3F32(dx, dy, dz);

            dir = Vec3F32.Normalise(dir);

            Orientation rot = bot.Rot;

            DirUtils.GetYawPitch(dir, out rot.RotY, out rot.HeadX);
            bot.Rot = rot;
        }
示例#8
0
        /// <summary> Gives distance (in half-pixel world units) from feet to camera height </summary>
        public static int CalcEyeHeight(Entity entity)
        {
            Vec3F32 scale = CalcScale(entity);
            string  model = GetRawModel(entity.Model);
            BlockID raw;

            if (BlockID.TryParse(model, out raw) && raw <= Block.MaxRaw)
            {
                return(16);                                                         //lazily return middle of full block if it thinks it's a block ID.
            }
            float eyeHeight = Get(model).EyeHeight;

            eyeHeight *= scale.Y;
            eyeHeight *= 2f; //multiply by two because world positions are measured in half-pixels
            return((int)eyeHeight);
        }
示例#9
0
        static bool MoveTowards(PlayerBot bot, Player p, Metadata meta)
        {
            if (p == null)
            {
                return(false);
            }
            int dist = (int)(0.875 * 32);

            int dx = p.Pos.X - bot.Pos.X, dy = p.Pos.Y - bot.Pos.Y, dz = p.Pos.Z - bot.Pos.Z;

            bot.TargetPos = p.Pos;
            bot.movement  = true;

            Vec3F32 dir = new Vec3F32(dx, dy, dz);

            dir = Vec3F32.Normalise(dir);
            Orientation rot = bot.Rot;

            DirUtils.GetYawPitch(dir, out rot.RotY, out rot.HeadX);

            MobAI.SetDirectionalSpeeds(bot);

            dx = Math.Abs(dx); dy = Math.Abs(dy); dz = Math.Abs(dz);
            //if (InRange(p, bot, dist)) p.Message("%cInfect");

            bot.Rot = rot;

            if (dx < (5 * 32) && dz < (5 * 32)) // 5 block reach
            {
                Random rnd = new Random();
                // This code serves as a sort of 'CPS mechanism' to ensure that the bot does not perfectly delete every single block
                int chance = rnd.Next(0, 4); // 33% chance of deleting the block
                if (chance < 3)
                {
                    bot.level.UpdateBlock(Player.Console, (ushort)(p.Pos.X / 32), (ushort)((p.Pos.Y / 32) - 2), (ushort)(p.Pos.Z / 32), Block.Air);

                    if ((p.Pos.Y / 32) > lastY)
                    {
                        bot.level.UpdateBlock(Player.Console, (ushort)(p.Pos.X / 32), (ushort)((p.Pos.Y / 32) - 3), (ushort)(p.Pos.Z / 32), Block.Air);
                    }
                }

                lastY = (p.Pos.Y / 32);
            }

            return(dx <= 8 && dy <= 16 && dz <= 8);
        }
            public void LoadFromFile()
            {
                string            path       = GetCCPath();
                string            contentsCC = File.ReadAllText(path);
                StoredCustomModel o          = JsonConvert.DeserializeObject <StoredCustomModel>(contentsCC, jsonSettings);

                this.nameY            = o.nameY;
                this.autoNameY        = o.autoNameY;
                this.eyeY             = o.eyeY;
                this.collisionBounds  = o.collisionBounds;
                this.pickingBoundsMin = o.pickingBoundsMin;
                this.pickingBoundsMax = o.pickingBoundsMax;
                this.bobbing          = o.bobbing;
                this.pushes           = o.pushes;
                this.usesHumanSkin    = o.usesHumanSkin;
                this.calcHumanAnims   = o.calcHumanAnims;
                this.defaultSkin      = o.defaultSkin;
            }
示例#11
0
        public static void GetYawPitch(Vec3F32 dir, out byte yaw, out byte pitch)
        {
            // y = -sin(pitch) -> pitch = arcsin(-y)
            // x = sin(yaw)    -> yaw = arcsin(x)
            // z = -cos(yaw)   -> yaw = arccos(-z)

            // We ignore the cos(pitch) multiplication by the x/z components, since
            // this does not affect the resulting yaw
            const double rad2Packed = 256.0 / (2 * Math.PI);

            // NOTE: This conversion method **does** lose information
            // a) If x and z are 0, yaw cannot be properly recalculated
            // b) Pitch will always be from 0-64 or 192-256, therefore flipped heads lost
            //    However since we have X/Z, this problem does not occur for yaw,
            //    as we can use both values to determine which side of unit circle yaw is in
            // c) Resulting yaw/pitch may be 1 or 2 values off due to rounding
            yaw   = (byte)(Math.Atan2(dir.X, -dir.Z) * rad2Packed);
            pitch = (byte)(Math.Asin(-dir.Y) * rad2Packed);
        }
示例#12
0
            // graceLength is how far (in pixels) you can extend past max width/height on all sides
            private static bool SizeAllowed(Vec3F32 boxCorner, float graceLength)
            {
                //convert to block-unit to match boxCorner
                const float maxWidthB    = maxWidth / 16f;
                const float maxHeightB   = maxHeight / 16f;
                float       graceLengthB = graceLength / 16f;

                if (
                    boxCorner.Y < -graceLengthB ||
                    boxCorner.Y > maxHeightB + graceLengthB ||

                    boxCorner.X < -((maxWidthB / 2) + graceLengthB) ||
                    boxCorner.X > (maxWidthB / 2) + graceLengthB ||
                    boxCorner.Z < -((maxWidthB / 2) + graceLengthB) ||
                    boxCorner.Z > (maxWidthB / 2) + graceLengthB
                    )
                {
                    return(false);
                }
                return(true);
            }
示例#13
0
        public static void HitPlayer(PlayerBot bot, Player p, Orientation rot)
        {
            // Send player backwards if hit
            // Code "borrowed" from PvP plugin

            int srcHeight = ModelInfo.CalcEyeHeight(bot);
            int dstHeight = ModelInfo.CalcEyeHeight(p);
            int dx2 = bot.Pos.X - p.Pos.X, dy2 = (bot.Pos.Y + srcHeight) - (p.Pos.Y + dstHeight), dz2 = bot.Pos.Z - p.Pos.Z;

            Vec3F32 dir2 = new Vec3F32(dx2, dy2, dz2);

            if (dir2.Length > 0)
            {
                dir2 = Vec3F32.Normalise(dir2);
            }

            float mult    = 1 / ModelInfo.GetRawScale(p.Model);
            float plScale = ModelInfo.GetRawScale(p.Model);

            float VelocityY = 1.0117f * mult;

            if (dir2.Length <= 0)
            {
                VelocityY = 0;
            }

            if (p.Supports(CpeExt.VelocityControl))
            {
                // Intensity of force is in part determined by model scale
                p.Send(Packet.VelocityControl((-dir2.X * mult) * 0.57f, VelocityY, (-dir2.Z * mult) * 0.57f, 0, 1, 0));
            }

            // If we are very close to a player, switch from trying to look
            // at them to just facing the opposite direction to them

            rot.RotY = (byte)(p.Rot.RotY + 128);
            bot.Rot  = rot;
        }
        static bool MoveTowards(PlayerBot bot, Player p)
        {
            int dx = p.Pos.X - bot.Pos.X, dy = p.Pos.Y - bot.Pos.Y, dz = p.Pos.Z - bot.Pos.Z;

            bot.TargetPos = p.Pos;
            bot.movement  = true;

            Vec3F32 dir = new Vec3F32(dx, dy, dz);

            dir = Vec3F32.Normalise(dir);
            Orientation rot = bot.Rot;

            DirUtils.GetYawPitch(dir, out rot.RotY, out rot.HeadX);

            // If we are very close to a player, switch from trying to look
            // at them to just facing the opposite direction to them
            if (Math.Abs(dx) < 4 && Math.Abs(dz) < 4)
            {
                rot.RotY = (byte)(p.Rot.RotY + 128);
            }
            bot.Rot = rot;

            return(dx <= 8 && dy <= 16 && dz <= 8);
        }
示例#15
0
        void OnPlayerMove(Player p, Position next, byte yaw, byte pitch)
        {
            string data = playerEffects.FindData(p.name);

            if (data == null)
            {
                return;
            }

            if (rnd.NextDouble() > 0.125f && !data.StartsWith("puff"))
            {
                return;
            }
            float  x          = p.Pos.X * 0.03125f;
            float  y          = (p.Pos.Y + ModelInfo.CalcEyeHeight(p) - Entities.CharacterHeight) * 0.03125f;
            float  z          = p.Pos.Z * 0.03125f;
            float  originX    = x;
            float  originY    = y;
            float  originZ    = z;
            Player notShownTo = null;

            //ugly hack
            if (data.StartsWith("leaf"))
            {
                if (rnd.NextDouble() > 0.5f)
                {
                    return;
                }
                originX += 32;
                originZ += 8;
            }
            else if (data.StartsWith("puff"))
            {
                Random    playerRandom = new Random(p.name.GetHashCode());
                const int cycle        = 4000;
                const int breatheOut   = 1000;
                int       offset       = playerRandom.Next(0, cycle + 1);

                TimeSpan delta  = DateTime.UtcNow - (startTime.AddMilliseconds(offset));
                int      ms     = (int)delta.TotalMilliseconds;
                bool     phase1 = (ms % cycle) < breatheOut;
                if (!phase1)
                {
                    return;
                }


                Vec3F32 dir = DirUtils.GetDirVector(yaw, pitch);
                dir.X     *= 0.3f;
                dir.Y     *= 0.3f;
                dir.Z     *= 0.3f;
                originY    = y;
                x         += dir.X;
                y         += dir.Y;
                z         += dir.Z;
                y         -= 0.15f;
                originY   -= 0.15f;
                notShownTo = p;
            }
            SpawnEffectAt(p.level, data, x, y, z, originX, originY, originZ);
        }
示例#16
0
                private Part ToPart(Element e)
                {
                    if (!e.visibility)
                    {
                        return(null);
                    }

                    Vec3F32 rotation = new Vec3F32 {
                        X = 0, Y = 0, Z = 0
                    };

                    if (e.rotation != null)
                    {
                        rotation.X = e.rotation[0];
                        rotation.Y = e.rotation[1];
                        rotation.Z = e.rotation[2];
                    }

                    Vec3F32 min = new Vec3F32 {
                        X = (e.from[0] - e.inflate) / 16.0f,
                        Y = (e.from[1] - e.inflate) / 16.0f,
                        Z = (e.from[2] - e.inflate) / 16.0f,
                    };
                    Vec3F32 max = new Vec3F32 {
                        X = (e.to[0] + e.inflate) / 16.0f,
                        Y = (e.to[1] + e.inflate) / 16.0f,
                        Z = (e.to[2] + e.inflate) / 16.0f,
                    };

                    var rotationOrigin = new Vec3F32 {
                        X = e.origin[0] / 16.0f,
                        Y = e.origin[1] / 16.0f,
                        Z = e.origin[2] / 16.0f,
                    };

                    // faces in order [u1, v1, u2, v2]
                    /* uv coords in order: top, bottom, front, back, left, right */
                    // swap up's uv's
                    UInt16[] u1 = new[] {
                        (UInt16)e.faces.up.uv[2],
                        (UInt16)e.faces.down.uv[0],
                        (UInt16)e.faces.north.uv[0],
                        (UInt16)e.faces.south.uv[0],
                        (UInt16)e.faces.east.uv[0],
                        (UInt16)e.faces.west.uv[0],
                    };
                    UInt16[] v1 = new[] {
                        (UInt16)e.faces.up.uv[3],
                        (UInt16)e.faces.down.uv[1],
                        (UInt16)e.faces.north.uv[1],
                        (UInt16)e.faces.south.uv[1],
                        (UInt16)e.faces.east.uv[1],
                        (UInt16)e.faces.west.uv[1],
                    };
                    UInt16[] u2 = new[] {
                        (UInt16)e.faces.up.uv[0],
                        (UInt16)e.faces.down.uv[2],
                        (UInt16)e.faces.north.uv[2],
                        (UInt16)e.faces.south.uv[2],
                        (UInt16)e.faces.east.uv[2],
                        (UInt16)e.faces.west.uv[2],
                    };
                    UInt16[] v2 = new[] {
                        (UInt16)e.faces.up.uv[1],
                        (UInt16)e.faces.down.uv[3],
                        (UInt16)e.faces.north.uv[3],
                        (UInt16)e.faces.south.uv[3],
                        (UInt16)e.faces.east.uv[3],
                        (UInt16)e.faces.west.uv[3],
                    };

                    var part = new Part {
                        min            = min,
                        max            = max,
                        u1             = u2,
                        v1             = v1,
                        u2             = u1,
                        v2             = v2,
                        rotationOrigin = rotationOrigin,
                        rotation       = rotation,
                    };

                    var anims    = new List <CustomModelAnim>();
                    var partName = e.name.Replace(" ", "");

                    foreach (var attr in partName.SplitComma())
                    {
                        float?a = null;
                        float?b = null;
                        float?c = null;
                        float?d = null;

                        var colonSplit = attr.Split(':');
                        var attrName   = colonSplit[0];
                        if (colonSplit.Length >= 2)
                        {
                            var modifiers = colonSplit[1].Replace(" ", "").Split('|');
                            if (modifiers.Length > 0)
                            {
                                a = float.Parse(modifiers[0]);
                                if (modifiers.Length > 1)
                                {
                                    b = float.Parse(modifiers[1]);
                                    if (modifiers.Length > 2)
                                    {
                                        c = float.Parse(modifiers[2]);
                                        if (modifiers.Length > 3)
                                        {
                                            d = float.Parse(modifiers[3]);
                                        }
                                    }
                                }
                            }
                        }


                        if (PartNamesToAnim.TryGetValue(attrName, out PartNameToAnim toAnim))
                        {
                            anims.AddRange(toAnim.ToAnim(attrName, a, b, c, d));
                        }
                        else if (attrName.CaselessEq("leftidle"))
                        {
                            anims.Add(new CustomModelAnim {
                                type = CustomModelAnimType.SinRotate,
                                axis = CustomModelAnimAxis.X,
                                a    = ANIM_IDLE_XPERIOD,
                                b    = ANIM_IDLE_MAX,
                                c    = 0,
                                d    = 0,
                            });
                            anims.Add(new CustomModelAnim {
                                type = CustomModelAnimType.SinRotate,
                                axis = CustomModelAnimAxis.Z,
                                a    = ANIM_IDLE_ZPERIOD,
                                b    = -ANIM_IDLE_MAX,
                                c    = 0.25f,
                                d    = 1,
                            });
                        }
                        else if (attrName.CaselessEq("rightidle"))
                        {
                            anims.Add(new CustomModelAnim {
                                type = CustomModelAnimType.SinRotate,
                                axis = CustomModelAnimAxis.X,
                                a    = ANIM_IDLE_XPERIOD,
                                b    = -ANIM_IDLE_MAX,
                                c    = 0,
                                d    = 0,
                            });
                            anims.Add(new CustomModelAnim {
                                type = CustomModelAnimType.SinRotate,
                                axis = CustomModelAnimAxis.Z,
                                a    = ANIM_IDLE_ZPERIOD,
                                b    = ANIM_IDLE_MAX,
                                c    = 0.25f,
                                d    = 1,
                            });
                        }
                        else if (attrName.CaselessEq("fullbright"))
                        {
                            part.fullbright = true;
                        }
                        else if (attrName.CaselessEq("hand"))
                        {
                            part.firstPersonArm = true;
                        }
                        else if (attrName.CaselessEq("layer"))
                        {
                            part.layer = true;
                        }
                        else if (attrName.CaselessEq("humanleftarm"))
                        {
                            part.skinLeftArm = true;
                        }
                        else if (attrName.CaselessEq("humanrightarm"))
                        {
                            part.skinRightArm = true;
                        }
                        else if (attrName.CaselessEq("humanleftleg"))
                        {
                            part.skinLeftLeg = true;
                        }
                        else if (attrName.CaselessEq("humanrightleg"))
                        {
                            part.skinRightLeg = true;
                        }
                    }
                    part.anims = anims.ToArray();

                    return(part);
                }