/// <summary>
        /// Calculate secondary attributes from primary attributes.
        /// i.e. How much critical strike chance does the characters agility provide?
        /// </summary>
        public override SecondaryAttributes CalculateSecondaryAttributes(PrimaryAttributes primaryAttributes)
        {
            // (Source: https://rankedboost.com/world-of-warcraft/classic-stats/)
            // 2 Melee Attack Power per 1 point of Strength.
            var meleeAttackPower = new MeleeAttackPower(primaryAttributes.Strength.Value * 2);
            // Block 1 Damage for every 20 points of Strength.
            var blockDamage = new BlockDamage(primaryAttributes.Strength.Value / 20);
            // 2 Armor for every 1 point of Agility.
            var armor = new ArmorAmount(primaryAttributes.Agility.Value / 2);
            // 1% Critical Strike Chance for every 20 points of Agility.
            var criticalStrike = new CriticalStrike(primaryAttributes.Agility.Value / 20);
            // 1 Ranged Attack Power per 1 point of Agility.
            var rangedAttackPower = new RangedAttackPower(primaryAttributes.Agility.Value);
            // 1% Dodge per 20 point of Agility.
            var dodge = new Dodge(primaryAttributes.Agility.Value / 20);
            // 5% base chance to Parry. (Source: https://worldofwarcraft.fandom.com/et/wiki/Parry)
            var parry = new Parry(5);
            // 10 Health for every 1 point of Stamina.
            var health = new Health((int)primaryAttributes.Stamina.Value / 10);

            var attributes = new SecondaryAttributes(
                health,
                criticalStrike,
                Hit.Zero,
                dodge,
                parry,
                Defense.Zero,
                blockDamage,
                meleeAttackPower,
                rangedAttackPower,
                armor,
                new WeaponSkills());

            return(attributes);
        }
 public virtual EntityShape GetShape(BlockDamage damage, out Location offset, bool shrink)
 {
     if ((shrink ? ShrunkBlockShapeCache : BlockShapeCache) != null)
     {
         offset = (shrink ? ShrunkOffsetCache : OffsetCache);
         return (shrink ? ShrunkBlockShapeCache : BlockShapeCache);
     }
     List<Vector3> vecs = GetVertices(new Vector3(0, 0, 0), false, false, false, false, false, false);
     Vector3 offs;
     if (vecs.Count == 0)
     {
         throw new Exception("No vertices for shape " + this);
     }
     if (shrink)
     {
         for (int i = 0; i < vecs.Count; i++)
         {
             vecs[i] = (vecs[i] - new Vector3(0.5f, 0.5f, 0.5f)) * SHRINK_CONSTANT + new Vector3(0.5f, 0.5f, 0.5f);
         }
     }
     ConvexHullShape shape = new ConvexHullShape(vecs, out offs) { CollisionMargin = 0 };
     offset = new Location(offs);
     if (shrink)
     {
         ShrunkBlockShapeCache = shape;
         ShrunkOffsetCache = offset;
     }
     else
     {
         BlockShapeCache = shape;
         OffsetCache = offset;
     }
     return shape;
 }
Exemple #3
0
 public BlockItemEntity(Region tregion, Material tmat, byte dat, byte tpaint, BlockDamage tdamage)
     : base(tregion, false, true)
 {
     Mat    = tmat;
     Dat    = dat;
     Paint  = tpaint;
     Damage = tdamage;
     Shape  = BlockShapeRegistry.BSD[dat].GetShape(Damage, out Offset, !(this is StaticBlockEntity));
     SetMass(20);
 }
Exemple #4
0
 public BlockItemEntity(Region tregion, Material tmat, byte dat, byte tpaint, BlockDamage tdamage)
     : base(tregion, false, true)
 {
     Mat = tmat;
     Dat = dat;
     Paint = tpaint;
     Damage = tdamage;
     Shape = BlockShapeRegistry.BSD[dat].GetShape(Damage, out Offset, !(this is StaticBlockEntity));
     SetMass(20);
 }
 private void OnCollisionEnter2D(Collision2D collision)
 {
     if (collision.gameObject.tag == "Destructable" && isReleased)
     {
         StartCoroutine(spriteChange());
         Object.Instantiate(particleSystem, base.gameObject.transform.position, base.gameObject.transform.rotation);
         BlockDamage component = collision.gameObject.GetComponent <BlockDamage>();
         component.minusHealth(damage);
         component.minusHealth(1);
     }
 }
Exemple #6
0
 public override void SetTextureName(string name)
 {
     if (name == null || name.Length == 0)
     {
         Tex = null;
     }
     else
     {
         if (name.Contains(":") && name.Before(":").ToLowerFast() == "render_block")
         {
             string[] blockDataToRender = name.After(":").SplitFast(',');
             if (blockDataToRender[0] == "self")
             {
                 BlockInternal bi = BlockInternal.FromItemDatum(Datum);
                 RenderedBlock = new BlockItemEntity(TheClient.TheRegion, bi.Material, bi.BlockData, bi.BlockPaint, bi.Damage);
                 RenderedBlock.GenVBO();
             }
             else
             {
                 Material    mat    = MaterialHelpers.FromNameOrNumber(blockDataToRender[0]);
                 byte        data   = (byte)(blockDataToRender.Length < 2 ? 0 : Utilities.StringToInt(blockDataToRender[1]));
                 byte        paint  = (byte)(blockDataToRender.Length < 3 ? 0 : Colors.ForName(blockDataToRender[2]));
                 BlockDamage damage = blockDataToRender.Length < 4 ? BlockDamage.NONE : (BlockDamage)Enum.Parse(typeof(BlockDamage), blockDataToRender[3], true);
                 RenderedBlock = new BlockItemEntity(TheClient.TheRegion, mat, data, paint, damage);
                 RenderedBlock.GenVBO();
             }
             Tex = null;
         }
         if (name.Contains(":") && name.Before(":").ToLowerFast() == "render_model")
         {
             string model = name.After(":");
             if (model.ToLowerFast() == "self")
             {
                 model = GetModelName();
             }
             RenderedModel = new ModelEntity(model, TheClient.TheRegion)
             {
                 Visible = true
             };
             RenderedModel.PreHandleSpawn();
             Tex = null;
         }
         else
         {
             Tex = TheClient.Textures.GetTexture(name);
         }
     }
 }
        public EntityShape GetShape(BlockDamage damage, out Location offset, bool shrink)
        {
            if (damage != DamageMode)
            {
                return(Damaged[(int)damage].GetShape(damage, out offset, shrink));
            }
            if ((shrink ? ShrunkBlockShapeCache : BlockShapeCache) != null)
            {
                offset = (shrink ? ShrunkOffsetCache : OffsetCache);
                EntityShape es = (shrink ? ShrunkBlockShapeCache : BlockShapeCache);
                es.ClearShapeChanged();
                return(es);
            }
            List <Vector3> vecs = GetVertices(new Vector3(0, 0, 0), false, false, false, false, false, false);

            if (vecs.Count == 0)
            {
                throw new Exception("No vertices for shape " + this);
            }
            if (shrink)
            {
                for (int i = 0; i < vecs.Count; i++)
                {
                    vecs[i] = (vecs[i] - new Vector3(0.5f, 0.5f, 0.5f)) * SHRINK_CONSTANT + new Vector3(0.5f, 0.5f, 0.5f);
                }
            }
            ConvexHullShape shape = new ConvexHullShape(vecs, out Vector3 offs)
            {
                CollisionMargin = 0
            };

            offset = new Location(offs);
            if (shrink)
            {
                ShrunkBlockShapeCache = shape;
                ShrunkOffsetCache     = offset;
            }
            else
            {
                BlockShapeCache = shape;
                OffsetCache     = offset;
            }
            return(shape);
        }
    }
    private void AddExplosionForce(Rigidbody2D rb, float explosionForce, Vector2 explodingPosition, float radius, float upwardsModifier = 0f, ForceMode2D mode = ForceMode2D.Impulse)
    {
        BlockDamage component = rb.GetComponent <BlockDamage>();

        if (canExplode)
        {
            explosieAudio.clip = explosie;
            Vector2 a         = rb.position - explodingPosition;
            float   magnitude = a.magnitude;
            explosieAudio.Play();
            if (magnitude < radius / 2f)
            {
                component.minusHealth(3);
            }
            else
            {
                if (magnitude > radius / 3f && magnitude < radius / 2f)
                {
                    component.minusHealth(2);
                }
                if (magnitude > radius && magnitude < radius / 3f)
                {
                    component.minusHealth(1);
                }
            }
            if (upwardsModifier == 0f)
            {
                a /= magnitude;
            }
            else
            {
                a.Normalize();
            }
            rb.AddForce(Mathf.Lerp(0f, explosionForce, radius / magnitude) * a, mode);
        }
        Object.Destroy(base.gameObject);
    }
 /// <summary>
 /// Sets a block and triggers physics around it.
 /// </summary>
 /// <param name="block">The block location.</param>
 /// <param name="mat">The material to set to.</param>
 /// <param name="dat">The shape to set to.</param>
 /// <param name="paint">The paint to set to.</param>
 /// <param name="damage">Te damage to set to.</param>
 public void PhysicsSetBlock(Location block, Material mat, byte dat = 0, byte paint = 0, BlockDamage damage = BlockDamage.NONE)
 {
     PhysUpdatedPush.Add(LoadChunk(ChunkLocFor(block)));
     SetBlockMaterial(block, mat, dat, paint, (byte)(BlockFlags.EDITED | BlockFlags.NEEDS_RECALC), damage, false);
     PhysBlockAnnounce(block);
     if (mat.GetSolidity() != MaterialSolidity.FULLSOLID)
     {
         PhysBlockAnnounce(block + new Location(1, 0, 0));
         PhysBlockAnnounce(block + new Location(-1, 0, 0));
         PhysBlockAnnounce(block + new Location(0, 0, 1));
         PhysBlockAnnounce(block + new Location(0, 0, -1));
         PhysBlockAnnounce(block + new Location(0, 1, 0));
         PhysBlockAnnounce(block + new Location(0, -1, 0));
     }
 }
 public void PhysicsSetBlock(Location block, Material mat, byte dat = 0, byte paint = 0, BlockDamage damage = BlockDamage.NONE)
 {
     SetBlockMaterial(block, mat, dat, paint, (byte)(BlockFlags.EDITED | BlockFlags.NEEDS_RECALC), damage);
     physThisTick++;
     if (physThisTick > 5)
     {
         physThisTick = 0;
         physBoost += 0.05;
     }
     TheServer.Schedule.ScheduleSyncTask(() => { SurroundRunPhysics(block); }, physBoost);
 }
Exemple #11
0
        public void SetBlockMaterial(Location pos, Material mat, byte dat = 0, byte paint = 0, byte locdat = (byte)BlockFlags.EDITED, BlockDamage damage = BlockDamage.NONE,
                                     bool broadcast = true, bool regen = true, bool override_protection    = false)
        {
            Chunk ch = LoadChunk(ChunkLocFor(pos));

            lock (ch.EditSessionLock)
            {
                int x = (int)Math.Floor(pos.X) - (int)ch.WorldPosition.X * Chunk.CHUNK_SIZE;
                int y = (int)Math.Floor(pos.Y) - (int)ch.WorldPosition.Y * Chunk.CHUNK_SIZE;
                int z = (int)Math.Floor(pos.Z) - (int)ch.WorldPosition.Z * Chunk.CHUNK_SIZE;
                if (!override_protection && ((BlockFlags)ch.GetBlockAt(x, y, z).BlockLocalData).HasFlag(BlockFlags.PROTECTED))
                {
                    return;
                }
                BlockInternal bi = new BlockInternal((ushort)mat, dat, paint, locdat)
                {
                    Damage = damage
                };
                ch.SetBlockAt(x, y, z, bi);
                ch.LastEdited = GlobalTickTime;
                ch.Flags     |= ChunkFlags.NEEDS_DETECT;
                ch.ChunkDetect();
                // TODO: See if this makes any new chunks visible!
                if (broadcast)
                {
                    // TODO: Send per-person based on chunk awareness details
                    ChunkSendToAll(new BlockEditPacketOut(new Location[] { pos }, new ushort[] { bi._BlockMaterialInternal }, new byte[] { dat }, new byte[] { paint }), ch.WorldPosition);
                }
            }
        }
 public void PhysicsSetBlock(Location block, Material mat, byte dat = 0, byte paint = 0, BlockDamage damage = BlockDamage.NONE)
 {
     SetBlockMaterial(block, mat, dat, paint, (byte)(BlockFlags.EDITED | BlockFlags.NEEDS_RECALC), damage);
     physThisTick++;
     if (physThisTick > 5)
     {
         physThisTick = 0;
         physBoost   += 0.05;
     }
     TheServer.Schedule.ScheduleSyncTask(() => { SurroundRunPhysics(block); }, physBoost);
 }
Exemple #13
0
 public void SetBlockMaterial(Location pos, Material mat, byte dat = 0, byte paint = 0, byte locdat = (byte)BlockFlags.EDITED, BlockDamage damage = BlockDamage.NONE,
     bool broadcast = true, bool regen = true, bool override_protection = false)
 {
     Chunk ch = LoadChunk(ChunkLocFor(pos));
     lock (ch.EditSessionLock)
     {
         int x = (int)Math.Floor(pos.X) - (int)ch.WorldPosition.X * Chunk.CHUNK_SIZE;
         int y = (int)Math.Floor(pos.Y) - (int)ch.WorldPosition.Y * Chunk.CHUNK_SIZE;
         int z = (int)Math.Floor(pos.Z) - (int)ch.WorldPosition.Z * Chunk.CHUNK_SIZE;
         if (!override_protection && ((BlockFlags)ch.GetBlockAt(x, y, z).BlockLocalData).HasFlag(BlockFlags.PROTECTED))
         {
             return;
         }
         BlockInternal bi = new BlockInternal((ushort)mat, dat, paint, locdat) { Damage = damage };
         ch.SetBlockAt(x, y, z, bi);
         ch.LastEdited = GlobalTickTime;
         ch.Flags |= ChunkFlags.NEEDS_DETECT;
         ch.ChunkDetect();
         // TODO: See if this makes any new chunks visible!
         if (broadcast)
         {
             // TODO: Send per-person based on chunk awareness details
             ChunkSendToAll(new BlockEditPacketOut(new Location[] { pos }, new ushort[] { bi._BlockMaterialInternal }, new byte[] { dat }, new byte[] { paint }), ch.WorldPosition);
         }
     }
 }