public override void OnHeldInteractStart(ItemSlot slot, EntityAgent byEntity, BlockSelection blockSel, EntitySelection entitySel, bool firstEvent, ref EnumHandHandling handHandling)
        {
            if (blockSel == null)
            {
                return;
            }

            ILiquidMetalSink be = byEntity.World.BlockAccessor.GetBlockEntity(blockSel.Position) as ILiquidMetalSink;

            if (be != null)
            {
                handHandling = EnumHandHandling.PreventDefault;
            }

            if (be != null && be.CanReceiveAny)
            {
                KeyValuePair <ItemStack, int> contents = GetContents(byEntity.World, slot.Itemstack);

                if (contents.Key == null)
                {
                    string emptiedCode = Attributes["emptiedBlockCode"].AsString();

                    slot.Itemstack = new ItemStack(byEntity.World.GetBlock(AssetLocation.Create(emptiedCode, Code.Domain)));
                    slot.MarkDirty();
                    handHandling = EnumHandHandling.PreventDefault;
                    return;
                }


                if (HasSolidifed(slot.Itemstack, contents.Key, byEntity.World))
                {
                    handHandling = EnumHandHandling.NotHandled;
                    return;
                }

                if (contents.Value <= 0)
                {
                    return;
                }
                if (!be.CanReceive(contents.Key))
                {
                    return;
                }
                be.BeginFill(blockSel.HitPosition);

                byEntity.World.RegisterCallback((world, pos, dt) =>
                {
                    if (byEntity.Controls.HandUse == EnumHandInteract.HeldItemInteract)
                    {
                        IPlayer byPlayer = null;
                        if (byEntity is EntityPlayer)
                        {
                            byPlayer = byEntity.World.PlayerByUid(((EntityPlayer)byEntity).PlayerUID);
                        }

                        world.PlaySoundAt(new AssetLocation("sounds/hotmetal"), byEntity, byPlayer);
                    }
                }, blockSel.Position, 666);

                handHandling = EnumHandHandling.PreventDefault;
            }
        }
Exemplo n.º 2
0
        protected override void Open(IWorldAccessor world, IPlayer byPlayer, BlockPos pos)
        {
            AssetLocation newCode = CodeWithVariant("state", IsOpened() ? "closed" : "opened");

            world.BlockAccessor.SetBlock(world.BlockAccessor.GetBlock(newCode).BlockId, pos);
        }
Exemplo n.º 3
0
 public static Item GetItem(this AssetLocation asset, ICoreAPI api)
 {
     return(api.World.GetItem(asset));
 }
Exemplo n.º 4
0
 public static int GetID(this AssetLocation loc, ICoreAPI Api) => loc.GetBlock(Api).BlockId;
Exemplo n.º 5
0
        private ClothSystem(ICoreAPI api, ClothManager cm, BlockPos originPos, float xsize, float zsize, EnumClothType clothType, AssetLocation ropeSectionModel = null)
        {
            this.clothType        = clothType;
            this.ropeSectionModel = ropeSectionModel;

            Init(api, cm);
            Random rand = api.World.Rand;

            bool hor         = rand.NextDouble() < 0.5;
            int  vertexIndex = 0;

            float step       = 1 / Resolution;
            int   numzpoints = (int)Math.Round(zsize * Resolution);
            int   numxpoints = (int)Math.Round(xsize * Resolution);

            if (clothType == EnumClothType.Rope)
            {
                numzpoints = 1;
            }

            float roughness  = 0.05f;
            int   k          = 0;
            int   pointIndex = 0;

            for (int z = 0; z < numzpoints; z++)
            {
                Points2d.Add(new PointList());

                for (int x = 0; x < numxpoints; x++)
                {
                    float dx = x * step;
                    float dy = z * step;
                    float dz = -roughness / 2 + (float)rand.NextDouble() * roughness;

                    if (hor)
                    {
                        dx = x * step;
                        dy = -roughness / 2 + (float)rand.NextDouble() * roughness;
                        dz = z * step;
                    }

                    var point = new ClothPoint(this, pointIndex++, originPos.X + dx, originPos.Y + dy, originPos.Z + dz);

                    Points2d[z].Points.Add(point);

                    int color = (k++ % 2) > 0 ? ColorUtil.WhiteArgb : ColorUtil.BlackArgb;

                    // add a vertical constraint
                    if (z > 0)
                    {
                        ClothPoint p1 = Points2d[z - 1].Points[x];
                        ClothPoint p2 = Points2d[z].Points[x];

                        var constraint = new ClothConstraint(p1, p2);
                        Constraints.Add(constraint);

                        if (capi != null)
                        {
                            if (LineDebug)
                            {
                                debugUpdateMesh.AddVertex(0, 0, 0, color);
                                debugUpdateMesh.AddVertex(0, 0, 0, color);

                                debugUpdateMesh.AddIndex(vertexIndex++);
                                debugUpdateMesh.AddIndex(vertexIndex++);
                            }
                        }
                    }

                    // add a new horizontal constraints
                    if (x > 0)
                    {
                        ClothPoint p1 = Points2d[z].Points[x - 1];
                        ClothPoint p2 = Points2d[z].Points[x];

                        var constraint = new ClothConstraint(p1, p2);
                        Constraints.Add(constraint);

                        if (capi != null)
                        {
                            if (LineDebug)
                            {
                                debugUpdateMesh.AddVertex(0, 0, 0, color);
                                debugUpdateMesh.AddVertex(0, 0, 0, color);

                                debugUpdateMesh.AddIndex(vertexIndex++);
                                debugUpdateMesh.AddIndex(vertexIndex++);
                            }
                        }
                    }
                }
            }



            if (capi != null && LineDebug)
            {
                debugUpdateMesh.mode = EnumDrawMode.Lines;
                debugMeshRef         = capi.Render.UploadMesh(debugUpdateMesh);

                debugUpdateMesh.Indices = null;
                debugUpdateMesh.Rgba    = null;
            }
        }
Exemplo n.º 6
0
        /// <summary>
        /// Will place all blocks using the supplied replace mode. Note: If you use a revertable or bulk block accessor you will have to call PlaceBlockEntities() after the Commit()
        /// </summary>
        /// <param name="blockAccessor"></param>
        /// <param name="worldForCollectibleResolve"></param>
        /// <param name="startPos"></param>
        /// <param name="mode"></param>
        /// <param name="replaceMetaBlocks"></param>
        /// <returns></returns>
        public virtual int PlaceReplacingBlocks(IBlockAccessor blockAccessor, IWorldAccessor worldForCollectibleResolve, BlockPos startPos, EnumReplaceMode mode, Dictionary <int, Dictionary <int, int> > replaceBlocks, bool replaceMetaBlocks = true)
        {
            BlockPos curPos = new BlockPos();
            int      placed = 0;

            PlaceBlockDelegate handler = null;

            switch (ReplaceMode)
            {
            case EnumReplaceMode.ReplaceAll:
                if (replaceMetaBlocks)
                {
                    handler = PlaceReplaceAllReplaceMeta;
                }
                else
                {
                    handler = PlaceReplaceAllKeepMeta;
                }
                break;

            case EnumReplaceMode.Replaceable:
                if (replaceMetaBlocks)
                {
                    handler = PlaceReplaceableReplaceMeta;
                }
                else
                {
                    handler = PlaceReplaceableKeepMeta;
                }
                break;

            case EnumReplaceMode.ReplaceAllNoAir:
                if (replaceMetaBlocks)
                {
                    handler = PlaceReplaceAllNoAirReplaceMeta;
                }
                else
                {
                    handler = PlaceReplaceAllNoAirKeepMeta;
                }
                break;

            case EnumReplaceMode.ReplaceOnlyAir:
                if (replaceMetaBlocks)
                {
                    handler = PlaceReplaceOnlyAirReplaceMeta;
                }
                else
                {
                    handler = PlaceReplaceOnlyAirKeepMeta;
                }
                break;
            }

            for (int i = 0; i < Indices.Count; i++)
            {
                uint index         = Indices[i];
                int  storedBlockid = BlockIds[i];

                int dx = (int)(index & 0x1ff);
                int dy = (int)((index >> 20) & 0x1ff);
                int dz = (int)((index >> 10) & 0x1ff);

                AssetLocation blockCode = BlockCodes[storedBlockid];

                Block newBlock = blockAccessor.GetBlock(blockCode);

                if (newBlock == null || (replaceMetaBlocks && newBlock == undergroundBlock))
                {
                    continue;
                }

                curPos.Set(dx + startPos.X, dy + startPos.Y, dz + startPos.Z);

                Block oldBlock = blockAccessor.GetBlock(curPos);

                Dictionary <int, int> replaceByBlock;
                if (replaceBlocks.TryGetValue(newBlock.Id, out replaceByBlock))
                {
                    int newBlockId;
                    if (replaceByBlock.TryGetValue(oldBlock.Id, out newBlockId))
                    {
                        newBlock = blockAccessor.GetBlock(newBlockId);
                    }
                }

                placed += handler(blockAccessor, curPos, oldBlock, newBlock);

                if (newBlock.LightHsv[2] > 0 && blockAccessor is IWorldGenBlockAccessor)
                {
                    ((IWorldGenBlockAccessor)blockAccessor).ScheduleBlockLightUpdate(curPos.Copy(), oldBlock.BlockId, newBlock.BlockId);
                }
            }

            if (!(blockAccessor is IBlockAccessorRevertable))
            {
                PlaceEntitiesAndBlockEntities(blockAccessor, worldForCollectibleResolve, startPos);
            }

            return(placed);
        }
Exemplo n.º 7
0
        public TextureAtlasPosition this[string textureCode]
        {
            get
            {
                AssetLocation texturePath;

                if (textureCode == "ropedcloth" || type == null || type == "")
                {
                    texturePath = new AssetLocation("block/cloth/ropedcloth");
                }
                else
                {
                    texturePath = new AssetLocation("block/cloth/tapestry/" + type);
                }

                AssetLocation cachedPath = texturePath.Clone();

                AssetLocation rotLoc = null;

                if (rotten)
                {
                    rotLoc           = new AssetLocation("block/cloth/tapestryoverlay/rotten" + rotVariant);
                    cachedPath.Path += "++" + rotLoc.Path;
                }

                TextureAtlasPosition texpos = capi.BlockTextureAtlas[cachedPath];

                if (texpos == null)
                {
                    IAsset texAsset = capi.Assets.TryGet(texturePath.Clone().WithPathPrefixOnce("textures/").WithPathAppendixOnce(".png"));
                    if (texAsset != null)
                    {
                        BitmapRef bmp = texAsset.ToBitmap(capi);

                        if (rotten)
                        {
                            BakedBitmap bakedBmp = new BakedBitmap()
                            {
                                Width = bmp.Width, Height = bmp.Height
                            };
                            bakedBmp.TexturePixels = bmp.Pixels;

                            int[] texturePixelsOverlay = capi.Assets.TryGet(rotLoc.WithPathPrefixOnce("textures/").WithPathAppendixOnce(".png"))?.ToBitmap(capi)?.Pixels;
                            if (texturePixelsOverlay == null)
                            {
                                throw new Exception("Texture file " + rotLoc + " is missing");
                            }

                            for (int p = 0; p < bakedBmp.TexturePixels.Length; p++)
                            {
                                bakedBmp.TexturePixels[p] = ColorUtil.ColorOver(texturePixelsOverlay[p], bakedBmp.TexturePixels[p]);
                            }

                            capi.BlockTextureAtlas.InsertTextureCached(cachedPath, bakedBmp, out _, out texpos);
                        }
                        else
                        {
                            capi.BlockTextureAtlas.InsertTextureCached(cachedPath, bmp, out _, out texpos);
                        }
                    }
                    else
                    {
                        capi.World.Logger.Warning("Tapestry type '{0}' defined texture '{1}', but no such texture found.", type, texturePath);
                    }
                }

                if (texpos == null)
                {
                    return(capi.BlockTextureAtlas.UnknownTexturePosition);
                }

                return(texpos);
            }
        }
        List <ResolvedBlockVariant> GatherVariants(RegistryObjectVariantGroup[] variantgroups, AssetLocation location)
        {
            List <ResolvedBlockVariant> blockvariantsFinal = new List <ResolvedBlockVariant>();

            if (variantgroups == null || variantgroups.Length == 0)
            {
                return(blockvariantsFinal);
            }

            OrderedDictionary <string, BlockVariant[]> blockvariantsMul = new OrderedDictionary <string, BlockVariant[]>();

            // 1. Collect all types
            for (int i = 0; i < variantgroups.Length; i++)
            {
                if (variantgroups[i].LoadFromProperties != null)
                {
                    CollectFromWorldProperties(variantgroups[i], variantgroups, blockvariantsMul, blockvariantsFinal, location);
                }

                if (variantgroups[i].States != null)
                {
                    CollectFromStateList(variantgroups[i], variantgroups, blockvariantsMul, blockvariantsFinal, location);
                }
            }

            // 2. Multiply multiplicative groups
            BlockVariant[,] variants = MultiplyProperties(blockvariantsMul.Values.ToArray());


            // 3. Add up multiplicative groups
            for (int i = 0; i < variants.GetLength(0); i++)
            {
                ResolvedBlockVariant resolved = new ResolvedBlockVariant();
                for (int j = 0; j < variants.GetLength(1); j++)
                {
                    BlockVariant variant = variants[i, j];

                    if (variant.Codes != null)
                    {
                        for (int k = 0; k < variant.Codes.Count; k++)
                        {
                            resolved.Codes.Add(variant.Types[k], variant.Codes[k]);
                        }
                    }
                    else
                    {
                        resolved.Codes.Add(blockvariantsMul.GetKeyAtIndex(j), variant.Code);
                    }
                }

                blockvariantsFinal.Add(resolved);
            }

            return(blockvariantsFinal);
        }
        private void CollectFromStateList(RegistryObjectVariantGroup variantGroup, RegistryObjectVariantGroup[] variantgroups, OrderedDictionary <string, BlockVariant[]> blockvariantsMul, List <ResolvedBlockVariant> blockvariantsFinal, AssetLocation filename)
        {
            if (variantGroup.Code == null)
            {
                api.Server.LogError(
                    "Error in itemtype {0}, a variantgroup using a state list must have a code. Ignoring.",
                    filename
                    );
                return;
            }

            string[] states = variantGroup.States;
            string   type   = variantGroup.Code;

            // Additive state list
            if (variantGroup.Combine == EnumCombination.Add)
            {
                for (int j = 0; j < states.Length; j++)
                {
                    ResolvedBlockVariant resolved = new ResolvedBlockVariant();
                    resolved.Codes.Add(type, states[j]);
                    blockvariantsFinal.Add(resolved);
                }
            }

            // Multiplicative state list
            if (variantGroup.Combine == EnumCombination.Multiply)
            {
                List <BlockVariant> stateList = new List <BlockVariant>();

                for (int j = 0; j < states.Length; j++)
                {
                    stateList.Add(new BlockVariant()
                    {
                        Code = states[j]
                    });
                }


                for (int i = 0; i < variantgroups.Length; i++)
                {
                    RegistryObjectVariantGroup cvg = variantgroups[i];
                    if (cvg.Combine == EnumCombination.SelectiveMultiply && cvg.OnVariant == variantGroup.Code)
                    {
                        for (int k = 0; k < stateList.Count; k++)
                        {
                            if (cvg.Code != stateList[k].Code)
                            {
                                continue;
                            }

                            BlockVariant old = stateList[k];

                            stateList.RemoveAt(k);

                            for (int j = 0; j < cvg.States.Length; j++)
                            {
                                List <string> codes = old.Codes == null ? new List <string>()
                                {
                                    old.Code
                                } : old.Codes;
                                List <string> types = old.Types == null ? new List <string>()
                                {
                                    variantGroup.Code
                                } : old.Types;

                                codes.Add(cvg.States[j]);
                                types.Add(cvg.Code);

                                stateList.Insert(k, new BlockVariant()
                                {
                                    Code  = old.Code + "-" + cvg.States[j],
                                    Codes = codes,
                                    Types = types
                                });
                            }
                        }
                    }
                }

                if (blockvariantsMul.ContainsKey(type))
                {
                    stateList.AddRange(blockvariantsMul[type]);
                    blockvariantsMul[type] = stateList.ToArray();
                }
                else
                {
                    blockvariantsMul.Add(type, stateList.ToArray());
                }
            }
        }
        Block baseBlockFromBlockType(BlockType blockType, AssetLocation fullcode, Dictionary <string, string> searchReplace)
        {
            BlockType typedBlockType = new BlockType()
            {
                Code          = blockType.Code,
                VariantGroups = blockType.VariantGroups,
                Enabled       = blockType.Enabled,
                jsonObject    = blockType.jsonObject.DeepClone() as JObject
            };

            try
            {
                solveByType(typedBlockType.jsonObject, fullcode.Path);
            }
            catch (Exception e)
            {
                api.Server.Logger.Error("Exception thrown while trying to resolve *byType properties of typed block {0}. Will ignore most of the attributes. Exception thrown: {1}", typedBlockType.Code, e);
            }

            try
            {
                JsonUtil.PopulateObject(typedBlockType, typedBlockType.jsonObject.ToString(), fullcode.Domain);
            }
            catch (Exception e)
            {
                api.Server.Logger.Error("Exception thrown while trying to populate/load json data of the typed block {0}. Will ignore most of the attributes. Exception thrown: {1}", typedBlockType.Code, e);
            }

            typedBlockType.jsonObject = null;
            Block block;

            if (api.ClassRegistry.GetBlockClass(typedBlockType.Class) == null)
            {
                api.Server.Logger.Error("Block with code {0} has defined a block class {1}, no such class registered. Will ignore.", typedBlockType.Code, typedBlockType.Class);
                block = new Block();
            }
            else
            {
                block = api.ClassRegistry.CreateBlock(typedBlockType.Class);
            }


            if (typedBlockType.EntityClass != null)
            {
                if (api.ClassRegistry.GetBlockEntity(typedBlockType.EntityClass) != null)
                {
                    block.EntityClass = typedBlockType.EntityClass;
                }
                else
                {
                    api.Server.Logger.Error("Block with code {0} has defined a block entity class {1}, no such class registered. Will ignore.", typedBlockType.Code, typedBlockType.EntityClass);
                }
            }

            block.Code                = fullcode;
            block.Class               = typedBlockType.Class;
            block.LiquidSelectable    = typedBlockType.LiquidSelectable;
            block.WalkSpeedMultiplier = typedBlockType.WalkspeedMultiplier;
            block.DragMultiplier      = typedBlockType.DragMultiplier;
            block.DrawType            = typedBlockType.DrawType;
            block.Replaceable         = typedBlockType.Replaceable;
            block.Fertility           = typedBlockType.Fertility;
            block.LightAbsorption     = typedBlockType.LightAbsorption;
            block.LightHsv            = typedBlockType.LightHsv;
            block.VertexFlags         = typedBlockType.VertexFlags?.Clone() ?? new VertexFlags(0);
            block.Resistance          = typedBlockType.Resistance;
            block.BlockMaterial       = typedBlockType.BlockMaterial;
            block.Shape               = typedBlockType.Shape;
            block.TexturesInventory   = typedBlockType.TexturesInventory;
            block.Textures            = typedBlockType.Textures;
            block.TintIndex           = typedBlockType.TintIndex;
            block.Ambientocclusion    = typedBlockType.Ambientocclusion;
            block.CollisionBoxes      = typedBlockType.CollisionBoxes == null ? null : (Cuboidf[])typedBlockType.CollisionBoxes.Clone();
            block.SelectionBoxes      = typedBlockType.SelectionBoxes == null ? null : (Cuboidf[])typedBlockType.SelectionBoxes.Clone();
            block.MaterialDensity     = typedBlockType.MaterialDensity;
            block.GuiTransform        = typedBlockType.GuiTransform;
            block.FpHandTransform     = typedBlockType.FpHandTransform;
            block.TpHandTransform     = typedBlockType.TpHandTransform;
            block.GroundTransform     = typedBlockType.GroundTransform;
            block.ShapeInventory      = typedBlockType.ShapeInventory;
            block.RenderPass          = typedBlockType.RenderPass;
            block.ParticleProperties  = typedBlockType.ParticleProperties;
            block.Climbable           = typedBlockType.Climbable;
            block.RainPermeable       = typedBlockType.RainPermeable;
            block.SnowCoverage        = typedBlockType.SnowCoverage;
            block.FaceCullMode        = typedBlockType.FaceCullMode;
            block.Drops               = typedBlockType.Drops;
            block.MaxStackSize        = typedBlockType.MaxStackSize;
            block.MatterState         = typedBlockType.MatterState;
            if (typedBlockType.Attributes != null)
            {
                block.Attributes = typedBlockType.Attributes.Clone();
            }
            block.NutritionProps     = typedBlockType.NutritionProps;
            block.GrindingProps      = typedBlockType.GrindingProps;
            block.LiquidLevel        = typedBlockType.LiquidLevel;
            block.AttackPower        = typedBlockType.AttackPower;
            block.MiningSpeed        = typedBlockType.MiningSpeed;
            block.MiningTier         = typedBlockType.MiningTier;
            block.RequiredMiningTier = typedBlockType.RequiredMiningTier;
            block.AttackRange        = typedBlockType.AttackRange;


            if (typedBlockType.Sounds != null)
            {
                block.Sounds = typedBlockType.Sounds.Clone();
            }
            block.RandomDrawOffset         = typedBlockType.RandomDrawOffset;
            block.RandomizeAxes            = typedBlockType.RandomizeAxes;
            block.CombustibleProps         = typedBlockType.CombustibleProps;
            block.StorageFlags             = (EnumItemStorageFlags)typedBlockType.StorageFlags;
            block.RenderAlphaTest          = typedBlockType.RenderAlphaTest;
            block.HeldTpHitAnimation       = typedBlockType.HeldTpHitAnimation;
            block.HeldTpIdleAnimation      = typedBlockType.HeldTpIdleAnimation;
            block.HeldTpUseAnimation       = typedBlockType.HeldTpUseAnimation;
            block.CreativeInventoryStacks  = typedBlockType.CreativeInventoryStacks == null ? null : (CreativeTabAndStackList[])typedBlockType.CreativeInventoryStacks.Clone();
            block.AllowSpawnCreatureGroups = (string[])typedBlockType.AllowSpawnCreatureGroups.Clone();

            if (block.CollisionBoxes != null)
            {
                for (int i = 0; i < block.CollisionBoxes.Length; i++)
                {
                    block.CollisionBoxes[i].RoundToFracsOf16();
                }
            }

            if (block.SelectionBoxes != null)
            {
                for (int i = 0; i < block.SelectionBoxes.Length; i++)
                {
                    block.SelectionBoxes[i].RoundToFracsOf16();
                }
            }

            typedBlockType.InitBlock(api.ClassRegistry, api.World.Logger, block, searchReplace);

            return(block);
        }
        public override void StartServerSide(ICoreServerAPI api)
        {
            this.api        = api;
            worldProperties = new Dictionary <AssetLocation, StandardWorldProperty>();

            foreach (var entry in api.Assets.GetMany <StandardWorldProperty>(api.Server.Logger, "worldproperties/"))
            {
                AssetLocation loc = entry.Key.Clone();
                loc.Path = loc.Path.Replace("worldproperties/", "");
                loc.RemoveEnding();
                worldProperties.Add(loc, entry.Value);
            }

            blockShapes = api.Assets.GetMany <Shape>(api.Server.Logger, "shapes/block/");

            blockTypes = new Dictionary <AssetLocation, BlockType>();
            foreach (KeyValuePair <AssetLocation, JObject> entry in api.Assets.GetMany <JObject>(api.Server.Logger, "blocktypes/"))
            {
                JToken        property        = null;
                JObject       blockTypeObject = entry.Value;
                AssetLocation location        = null;
                try
                {
                    location        = blockTypeObject.GetValue("code").ToObject <AssetLocation>();
                    location.Domain = entry.Key.Domain;
                }
                catch (Exception e)
                {
                    api.World.Logger.Error("Block type {0} has no valid code property. Will ignore. Exception thrown: {1}", entry.Key, e);
                    continue;
                }


                blockTypes.Add(entry.Key, new BlockType()
                {
                    Code          = location,
                    VariantGroups = blockTypeObject.TryGetValue("variantgroups", out property) ? property.ToObject <RegistryObjectVariantGroup[]>() : null,
                    Enabled       = blockTypeObject.TryGetValue("enabled", out property) ? property.ToObject <bool>() : true,
                    jsonObject    = blockTypeObject
                });
            }

            itemTypes = new Dictionary <AssetLocation, ItemType>();
            foreach (KeyValuePair <AssetLocation, JObject> entry in api.Assets.GetMany <JObject>(api.Server.Logger, "itemtypes/"))
            {
                JToken  property       = null;
                JObject itemTypeObject = entry.Value;

                AssetLocation location = itemTypeObject.GetValue("code").ToObject <AssetLocation>();
                location.Domain = entry.Key.Domain;

                itemTypes.Add(entry.Key, new ItemType()
                {
                    Code          = location,
                    VariantGroups = itemTypeObject.TryGetValue("variantgroups", out property) ? property.ToObject <RegistryObjectVariantGroup[]>() : null,
                    Enabled       = itemTypeObject.TryGetValue("enabled", out property) ? property.ToObject <bool>() : true,
                    jsonObject    = itemTypeObject
                });
            }

            entityTypes = new Dictionary <AssetLocation, EntityType>();
            foreach (KeyValuePair <AssetLocation, JObject> entry in api.Assets.GetMany <JObject>(api.Server.Logger, "entities/"))
            {
                JToken        property        = null;
                JObject       blockTypeObject = entry.Value;
                AssetLocation location        = null;
                try
                {
                    location        = blockTypeObject.GetValue("code").ToObject <AssetLocation>();
                    location.Domain = entry.Key.Domain;
                }
                catch (Exception e)
                {
                    api.World.Logger.Error("Entity type {0} has no valid code property. Will ignore. Exception thrown: {1}", entry.Key, e);
                    continue;
                }

                try
                {
                    entityTypes.Add(entry.Key, new EntityType()
                    {
                        Code          = location,
                        VariantGroups = blockTypeObject.TryGetValue("variantgroups", out property) ? property.ToObject <RegistryObjectVariantGroup[]>() : null,
                        Enabled       = blockTypeObject.TryGetValue("enabled", out property) ? property.ToObject <bool>() : true,
                        jsonObject    = blockTypeObject
                    });
                } catch (Exception e)
                {
                    api.World.Logger.Error("Entity type {0} could not be loaded. Will ignore. Exception thrown: {1}", entry.Key, e);
                    continue;
                }
            }

            worldPropertiesVariants = new Dictionary <AssetLocation, BlockVariant[]>();
            foreach (var val in worldProperties)
            {
                if (val.Value == null)
                {
                    continue;
                }

                WorldPropertyVariant[] variants = val.Value.Variants;
                if (variants == null)
                {
                    continue;
                }

                if (val.Value.Code == null)
                {
                    api.Server.LogError("Error in worldproperties {0}, not code set", val.Key);
                    return;
                }

                worldPropertiesVariants[val.Value.Code] = new BlockVariant[variants.Length];

                for (int i = 0; i < variants.Length; i++)
                {
                    worldPropertiesVariants[val.Value.Code][i] = new BlockVariant()
                    {
                        Code = variants[i].Code.Path
                    };
                }
            }

            LoadEntities();
            LoadItems();
            LoadBlocks();

            api.Server.LogNotification("BlockLoader: Entities, Blocks and Items loaded");
        }
        Item baseItemFromItemType(ItemType itemType, AssetLocation fullcode, Dictionary <string, string> searchReplace)
        {
            ItemType typedItemType = new ItemType()
            {
                Code          = itemType.Code,
                VariantGroups = itemType.VariantGroups,
                Enabled       = itemType.Enabled,
                jsonObject    = itemType.jsonObject.DeepClone() as JObject
            };

            solveByType(typedItemType.jsonObject, fullcode.Path);

            try
            {
                JsonUtil.PopulateObject(typedItemType, typedItemType.jsonObject.ToString(), fullcode.Domain);
            }
            catch (Exception e)
            {
                api.Server.Logger.Error("Exception thrown while trying to populate/load json data of the typed item with code {0}. Will ignore most of the attributes. Exception: {1}", typedItemType.Code, e);
            }

            typedItemType.jsonObject = null;
            Item item;

            if (api.ClassRegistry.GetItemClass(typedItemType.Class) == null)
            {
                api.Server.Logger.Error("Item with code {0} has defined an item class {1}, but no such class registered. Will ignore.", typedItemType.Code, typedItemType.Class);
                item = new Item();
            }
            else
            {
                item = api.ClassRegistry.CreateItem(typedItemType.Class);
            }


            item.Code            = fullcode;
            item.Class           = typedItemType.Class;
            item.Textures        = typedItemType.Textures;
            item.MaterialDensity = typedItemType.MaterialDensity;
            item.GuiTransform    = typedItemType.GuiTransform;
            item.FpHandTransform = typedItemType.FpHandTransform;
            item.TpHandTransform = typedItemType.TpHandTransform;
            item.GroundTransform = typedItemType.GroundTransform;
            item.DamagedBy       = typedItemType.DamagedBy;
            item.MaxStackSize    = typedItemType.MaxStackSize;
            if (typedItemType.Attributes != null)
            {
                item.Attributes = typedItemType.Attributes;
            }
            item.CombustibleProps        = typedItemType.CombustibleProps;
            item.NutritionProps          = typedItemType.NutritionProps;
            item.GrindingProps           = typedItemType.GrindingProps;
            item.Shape                   = typedItemType.Shape;
            item.Tool                    = typedItemType.Tool;
            item.AttackPower             = typedItemType.AttackPower;
            item.LiquidSelectable        = typedItemType.LiquidSelectable;
            item.MiningTier              = typedItemType.MiningTier;
            item.Durability              = typedItemType.Durability;
            item.MiningSpeed             = typedItemType.MiningSpeed;
            item.AttackRange             = typedItemType.AttackRange;
            item.StorageFlags            = (EnumItemStorageFlags)typedItemType.StorageFlags;
            item.RenderAlphaTest         = typedItemType.RenderAlphaTest;
            item.HeldTpHitAnimation      = typedItemType.HeldTpHitAnimation;
            item.HeldTpIdleAnimation     = typedItemType.HeldTpIdleAnimation;
            item.HeldTpUseAnimation      = typedItemType.HeldTpUseAnimation;
            item.CreativeInventoryStacks = typedItemType.CreativeInventoryStacks == null ? null : (CreativeTabAndStackList[])typedItemType.CreativeInventoryStacks.Clone();
            item.MatterState             = typedItemType.MatterState;

            typedItemType.InitItem(api.ClassRegistry, item, searchReplace);

            return(item);
        }
Exemplo n.º 13
0
        private void ApplyPatch(int patchIndex, AssetLocation patchSourcefile, JsonPatch jsonPatch, ref int applied, ref int notFound, ref int errorCount)
        {
            if (jsonPatch.SideType != EnumAppSide.Universal && jsonPatch.SideType != api.Side)
            {
                return;
            }

            var path = jsonPatch.File.Path;

            if (!path.EndsWith(".json"))
            {
                path += ".json";
            }

            var asset = api.Assets.TryGet(path);

            if (asset == null)
            {
                api.World.Logger.VerboseDebug("Patch {0} in {1}: File {2} not found", patchIndex, patchSourcefile, path);
                notFound++;
                return;
            }

            Operation op = null;

            switch (jsonPatch.Op)
            {
            case EnumJsonPatchOp.Add:
                if (jsonPatch.Value == null)
                {
                    api.World.Logger.Error("Patch {0} in {1} failed probably because it is an add operation and the value property is not set or misspelled", patchIndex, patchSourcefile);
                    errorCount++;
                    return;
                }
                op = new AddOperation()
                {
                    Path = new Tavis.JsonPointer(jsonPatch.Path), Value = jsonPatch.Value.Token
                };
                break;

            case EnumJsonPatchOp.Remove:
                op = new RemoveOperation()
                {
                    Path = new Tavis.JsonPointer(jsonPatch.Path)
                };
                break;

            case EnumJsonPatchOp.Replace:
                if (jsonPatch.Value == null)
                {
                    api.World.Logger.Error("Patch {0} in {1} failed probably because it is a replace operation and the value property is not set or misspelled", patchIndex, patchSourcefile);
                    errorCount++;
                    return;
                }

                op = new ReplaceOperation()
                {
                    Path = new Tavis.JsonPointer(jsonPatch.Path), Value = jsonPatch.Value.Token
                };
                break;

            case EnumJsonPatchOp.Copy:
                op = new CopyOperation()
                {
                    Path = new Tavis.JsonPointer(jsonPatch.Path), FromPath = new JsonPointer(jsonPatch.FromPath)
                };
                break;

            case EnumJsonPatchOp.Move:
                op = new MoveOperation()
                {
                    Path = new Tavis.JsonPointer(jsonPatch.Path), FromPath = new JsonPointer(jsonPatch.FromPath)
                };
                break;
            }

            PatchDocument patchdoc = new PatchDocument(op);
            JToken        token    = null;

            try
            {
                token = JToken.Parse(asset.ToText());
            }
            catch (Exception e)
            {
                api.World.Logger.Error("Patch {0} in {1} failed probably because the syntax of the value is broken: {2}", patchIndex, patchSourcefile, e);
                errorCount++;
                return;
            }

            try
            {
                patchdoc.ApplyTo(token);
            }
            catch (Tavis.PathNotFoundException p)
            {
                api.World.Logger.Error("Patch {0} in {1} failed because supplied path {2} is invalid: {3}", patchIndex, patchSourcefile, jsonPatch.Path, p.Message);
                errorCount++;
                return;
            }
            catch (Exception e)
            {
                api.World.Logger.Error("Patch {0} in {1} failed, following Exception was thrown: {2}", patchIndex, patchSourcefile, e.Message);
                errorCount++;
                return;
            }

            string text = token.ToString();

            asset.Data = System.Text.Encoding.UTF8.GetBytes(text);

            applied++;
        }
Exemplo n.º 14
0
        public override bool OnHeldInteractStep(float secondsUsed, ItemSlot slot, EntityAgent byEntity, BlockSelection blockSel, EntitySelection entitySel)
        {
            if (blockSel == null)
            {
                return(false);
            }

            ILiquidMetalSink be = byEntity.World.BlockAccessor.GetBlockEntity(blockSel.Position) as ILiquidMetalSink;

            if (be == null)
            {
                return(false);
            }

            if (!be.CanReceiveAny)
            {
                return(false);
            }
            KeyValuePair <ItemStack, int> contents = GetContents(byEntity.World, slot.Itemstack);

            if (!be.CanReceive(contents.Key))
            {
                return(false);
            }

            float speed = 1.5f;
            float temp  = GetTemperature(byEntity.World, slot.Itemstack);

            if (byEntity.World is IClientWorldAccessor)
            {
                ModelTransform tf = new ModelTransform();
                tf.EnsureDefaultValues();

                tf.Origin.Set(0.5f, 0.2f, 0.5f);
                tf.Translation.Set(0, 0, -Math.Min(0.25f, speed * secondsUsed / 4));
                tf.Scale      = 1f + Math.Min(0.25f, speed * secondsUsed / 4);
                tf.Rotation.X = Math.Max(-110, -secondsUsed * 90 * speed);
                byEntity.Controls.UsingHeldItemTransformBefore = tf;
            }

            IPlayer byPlayer = null;

            if (byEntity is EntityPlayer)
            {
                byPlayer = byEntity.World.PlayerByUid(((EntityPlayer)byEntity).PlayerUID);
            }


            if (secondsUsed > 1 / speed)
            {
                if ((int)(30 * secondsUsed) % 3 == 1)
                {
                    Vec3d pos =
                        byEntity.Pos.XYZ
                        .Ahead(0.1f, byEntity.Pos.Pitch, byEntity.Pos.Yaw)
                        .Ahead(1.0f, byEntity.Pos.Pitch, byEntity.Pos.Yaw - GameMath.PIHALF)
                    ;
                    pos.Y += byEntity.LocalEyePos.Y - 0.4f;

                    smokePouring.MinPos = pos.AddCopy(-0.15, -0.15, -0.15);

                    Vec3d blockpos = blockSel.Position.ToVec3d().Add(0.5, 0.2, 0.5);

                    bigMetalSparks.MinQuantity = Math.Max(0.2f, 1 - (secondsUsed - 1) / 4);

                    if ((int)(30 * secondsUsed) % 7 == 1)
                    {
                        bigMetalSparks.MinPos = pos;
                        bigMetalSparks.MinVelocity.Set(-2, -1, -2);
                        bigMetalSparks.AddVelocity.Set(4, 1, 4);
                        byEntity.World.SpawnParticles(bigMetalSparks, byPlayer);

                        byEntity.World.SpawnParticles(smokePouring, byPlayer);
                    }

                    float     y2       = 0;
                    Block     block    = byEntity.World.BlockAccessor.GetBlock(blockSel.Position);
                    Cuboidf[] collboxs = block.GetCollisionBoxes(byEntity.World.BlockAccessor, blockSel.Position);
                    for (int i = 0; collboxs != null && i < collboxs.Length; i++)
                    {
                        y2 = Math.Max(y2, collboxs[i].Y2);
                    }

                    // Metal Spark on the mold
                    bigMetalSparks.MinVelocity.Set(-2, 1, -2);
                    bigMetalSparks.AddVelocity.Set(4, 5, 4);
                    bigMetalSparks.MinPos = blockpos.AddCopy(-0.25, y2 - 2 / 16f, -0.25);
                    bigMetalSparks.AddPos.Set(0.5, 0, 0.5);
                    bigMetalSparks.VertexFlags = (byte)GameMath.Clamp((int)temp - 770, 48, 128);
                    byEntity.World.SpawnParticles(bigMetalSparks, byPlayer);

                    // Smoke on the mold
                    byEntity.World.SpawnParticles(
                        Math.Max(1, 12 - (secondsUsed - 1) * 6),
                        ColorUtil.ToRgba(50, 220, 220, 220),
                        blockpos.AddCopy(-0.5, y2 - 2 / 16f, -0.5),
                        blockpos.Add(0.5, y2 - 2 / 16f + 0.15, 0.5),
                        new Vec3f(-0.5f, 0f, -0.5f),
                        new Vec3f(0.5f, 0f, 0.5f),
                        1.5f,
                        -0.05f,
                        0.75f,
                        EnumParticleModel.Quad,
                        byPlayer
                        );
                }

                int transferedAmount = Math.Min(2, contents.Value);


                be.ReceiveLiquidMetal(contents.Key, ref transferedAmount, temp);

                int newAmount = Math.Max(0, contents.Value - (2 - transferedAmount));
                slot.Itemstack.Attributes.SetInt("units", newAmount);


                if (newAmount <= 0 && byEntity.World is IServerWorldAccessor)
                {
                    string emptiedCode = Attributes["emptiedBlockCode"].AsString();
                    slot.Itemstack = new ItemStack(byEntity.World.GetBlock(AssetLocation.Create(emptiedCode, Code.Domain)));
                    slot.MarkDirty();
                    // Since we change the item stack we have to call this ourselves
                    OnHeldInteractStop(secondsUsed, slot, byEntity, blockSel, entitySel);
                    return(false);
                }

                return(true);
            }

            return(true);
        }
Exemplo n.º 15
0
        public Block GetHarvestedBlock(IWorldAccessor world)
        {
            AssetLocation newBlockCode = Code.CopyWithPath(Code.Path.Replace(normalCodePart, harvestedCodePart));

            return(world.GetBlock(newBlockCode));
        }
        private void CollectFromWorldProperties(RegistryObjectVariantGroup variantGroup, RegistryObjectVariantGroup[] variantgroups, OrderedDictionary <string, BlockVariant[]> blockvariantsMul, List <ResolvedBlockVariant> blockvariantsFinal, AssetLocation location)
        {
            StandardWorldProperty property = GetWorldPropertyByCode(variantGroup.LoadFromProperties);

            if (property == null)
            {
                api.Server.LogError(
                    "Error in item or block {0}, worldproperty {1} does not exist (or is empty). Ignoring.",
                    location, variantGroup.LoadFromProperties
                    );
                return;
            }

            string typename = variantGroup.Code == null ? property.Code.Path : variantGroup.Code;

            if (variantGroup.Combine == EnumCombination.Add)
            {
                foreach (WorldPropertyVariant variant in property.Variants)
                {
                    ResolvedBlockVariant resolved = new ResolvedBlockVariant();
                    resolved.Codes.Add(typename, variant.Code.Path);
                    blockvariantsFinal.Add(resolved);
                }
            }

            if (variantGroup.Combine == EnumCombination.Multiply)
            {
                blockvariantsMul.Add(typename, worldPropertiesVariants[property.Code]);
            }
        }
        public override void Initialize(EntityProperties properties, ICoreAPI api, long InChunkIndex3d)
        {
            if (removedBlockentity != null)
            {
                this.blockEntityAttributes = new TreeAttribute();
                removedBlockentity.ToTreeAttributes(blockEntityAttributes);
                blockEntityClass = api.World.ClassRegistry.GetBlockEntityClass(removedBlockentity.GetType());
            }

            SimulationRange = (int)(0.75f * GlobalConstants.DefaultTrackingRange);
            base.Initialize(properties, api, InChunkIndex3d);

            // Need to capture this now before we remove the block and start to fall
            drops = Block.GetDrops(api.World, initialPos, null);

            lightHsv = Block.GetLightHsv(World.BlockAccessor, initialPos);

            SidedPos.Motion.Y = -0.02;

            if (drops != null && drops.Length > 0)
            {
                stackForParticleColor = drops[0];
            }
            else
            {
                stackForParticleColor = new ItemStack(Block);
            }

            if (api.Side == EnumAppSide.Client && fallSound != null && fallingNow.Count < 100)
            {
                fallingNow.Add(EntityId);
                ICoreClientAPI capi = api as ICoreClientAPI;
                sound = capi.World.LoadSound(new SoundParams()
                {
                    Location  = fallSound.WithPathPrefixOnce("sounds/").WithPathAppendixOnce(".ogg"),
                    Position  = new Vec3f((float)Pos.X, (float)Pos.Y, (float)Pos.Z),
                    Range     = 32,
                    Pitch     = 0.8f + (float)capi.World.Rand.NextDouble() * 0.3f,
                    Volume    = 1,
                    SoundType = EnumSoundType.Ambient
                });
                sound.Start();
                soundStartDelay = 0.05f + (float)capi.World.Rand.NextDouble() / 3f;
            }

            canFallSideways = WatchedAttributes.GetBool("canFallSideways");
            dustIntensity   = WatchedAttributes.GetFloat("dustIntensity");


            if (WatchedAttributes.HasAttribute("fallSound"))
            {
                fallSound = new AssetLocation(WatchedAttributes.GetString("fallSound"));
            }

            if (api.World.Side == EnumAppSide.Client)
            {
                particleSys = api.ModLoader.GetModSystem <FallingBlockParticlesModSystem>();
                particleSys.Register(this);
                physicsBh = GetBehavior <EntityBehaviorPassivePhysics>();
            }
        }
        public override bool ShouldExecute()
        {
            if (entity.World.Rand.NextDouble() < 0.005)
            {
                return(false);
            }
            // Don't search more often than every 15 seconds
            if (lastPOISearchTotalMs + 15000 > entity.World.ElapsedMilliseconds)
            {
                return(false);
            }
            if (cooldownUntilMs > entity.World.ElapsedMilliseconds)
            {
                return(false);
            }
            if (cooldownUntilTotalHours > entity.World.Calendar.TotalHours)
            {
                return(false);
            }
            if (whenInEmotionState != null && !entity.HasEmotionState(whenInEmotionState))
            {
                return(false);
            }
            if (whenNotInEmotionState != null && entity.HasEmotionState(whenNotInEmotionState))
            {
                return(false);
            }

            EntityBehaviorMultiply bh = entity.GetBehavior <EntityBehaviorMultiply>();

            if (bh != null && !bh.ShouldEat && entity.World.Rand.NextDouble() < 0.996)
            {
                return(false);                                                                       // 0.4% chance go to the food source anyway just because (without eating anything).
            }
            targetPoi            = null;
            extraTargetDist      = 0;
            lastPOISearchTotalMs = entity.World.ElapsedMilliseconds;

            entity.World.Api.ModLoader.GetModSystem <EntityPartitioning>().WalkEntities(entity.ServerPos.XYZ, 10, (e) =>
            {
                if (e is EntityItem)
                {
                    EntityItem ei        = (EntityItem)e;
                    EnumFoodCategory?cat = ei.Itemstack?.Collectible?.NutritionProps?.FoodCategory;
                    if (cat != null && eatItemCategories.Contains((EnumFoodCategory)cat))
                    {
                        targetPoi = new LooseItemFoodSource(ei);
                        return(false);
                    }

                    AssetLocation code = ei.Itemstack?.Collectible?.Code;
                    if (code != null && eatItemCodes.Contains(code))
                    {
                        targetPoi = new LooseItemFoodSource(ei);
                        return(false);
                    }
                }

                if (searchPlayerInv && e is EntityPlayer eplr)
                {
                    if (eplr.Player.InventoryManager.Find(slot => slot.Inventory is InventoryBasePlayer && !slot.Empty && eatItemCodes.Contains(slot.Itemstack.Collectible.Code)))
                    {
                        targetPoi = new PlayerPoi(eplr);
                    }
                }

                return(true);
            });

            if (targetPoi == null)
            {
                targetPoi = porregistry.GetNearestPoi(entity.ServerPos.XYZ, 48, (poi) =>
                {
                    if (poi.Type != "food")
                    {
                        return(false);
                    }
                    IAnimalFoodSource foodPoi;

                    if ((foodPoi = poi as IAnimalFoodSource)?.IsSuitableFor(entity) == true)
                    {
                        FailedAttempt attempt;
                        failedSeekTargets.TryGetValue(foodPoi, out attempt);
                        if (attempt == null || (attempt.Count < 4 || attempt.LastTryMs < world.ElapsedMilliseconds - 60000))
                        {
                            return(true);
                        }
                    }

                    return(false);
                }) as IAnimalFoodSource;
            }

            /*if (targetPoi != null)
             * {
             *  if (targetPoi is BlockEntity || targetPoi is Block)
             *  {
             *      Block block = entity.World.BlockAccessor.GetBlock(targetPoi.Position.AsBlockPos);
             *      Cuboidf[] collboxes = block.GetCollisionBoxes(entity.World.BlockAccessor, targetPoi.Position.AsBlockPos);
             *      if (collboxes != null && collboxes.Length != 0 && collboxes[0].Y2 > 0.3f)
             *      {
             *          extraTargetDist = 0.15f;
             *      }
             *  }
             * }*/

            return(targetPoi != null);
        }
        private async Task <DownloadedAsset> DownloadBlobAsync(HttpClient client,
                                                               Build build,
                                                               Asset asset,
                                                               AssetLocation assetLocation,
                                                               string subPath,
                                                               List <string> errors)
        {
            // Normalize the asset name.  Sometimes the upload to the BAR will have
            // "assets/" prepended to it and sometimes not (depending on the Maestro tasks version).
            // Remove assets/ if it exists so we get consistent target paths.
            string normalizedAssetName = asset.Name;

            if (asset.Name.StartsWith("assets/"))
            {
                normalizedAssetName = asset.Name.Substring("assets/".Length);
            }

            string fullTargetPath = Path.Combine(subPath, assetsSubPath, normalizedAssetName);

            DownloadedAsset downloadedAsset = new DownloadedAsset()
            {
                Successful     = false,
                Asset          = asset,
                TargetLocation = fullTargetPath
            };

            // If the location is a blob storage account ending in index.json, as would be expected
            // if PushToBlobFeed was used, strip off the index.json and append the asset name. If that doesn't work,
            // prepend "assets/" to the asset name and try that.
            // When uploading assets via the PushToBlobFeed task, assets/ may be prepended (e.g. assets/symbols/)
            // upon upload, but may not be reported to the BAR, or may be reported to BAR.
            // Either way, normalize so that we end up with only one assets/ prepended.

            if (IsBlobFeedUrl(assetLocation.Location))
            {
                string finalBaseUri = assetLocation.Location.Substring(0, assetLocation.Location.Length - "index.json".Length);
                string finalUri1    = $"{finalBaseUri}{asset.Name}";
                string finalUri2    = $"{finalBaseUri}assets/{asset.Name}";
                if (await DownloadFileAsync(client, finalUri1, fullTargetPath, errors))
                {
                    downloadedAsset.Successful     = true;
                    downloadedAsset.SourceLocation = finalUri1;
                    return(downloadedAsset);
                }
                if (await DownloadFileAsync(client, finalUri2, fullTargetPath, errors))
                {
                    downloadedAsset.Successful     = true;
                    downloadedAsset.SourceLocation = finalUri2;
                    return(downloadedAsset);
                }
                // Could be under assets/assets/ in some recent builds due to a bug in the release
                // pipeline.
                if (!_options.NoWorkarounds)
                {
                    string finalUri3 = $"{finalBaseUri}assets/assets/{asset.Name}";
                    if (await DownloadFileAsync(client, finalUri3, fullTargetPath, errors))
                    {
                        downloadedAsset.Successful     = true;
                        downloadedAsset.SourceLocation = finalUri3;
                        return(downloadedAsset);
                    }
                }
                return(downloadedAsset);
            }
            else if (IsAzureDevOpsArtifactsUrl(assetLocation.Location))
            {
                // Do not attempt to download from AzDO.
                return(downloadedAsset);
            }

            if (string.IsNullOrEmpty(assetLocation.Location))
            {
                errors.Add($"Asset location for {asset.Name} is not available.");
            }
            else
            {
                errors.Add($"Blob uri '{assetLocation.Location} for {asset.Name} is of an unknown type");
            }
            return(downloadedAsset);
        }
        public override void LoadConfig(JsonObject taskConfig, JsonObject aiConfig)
        {
            base.LoadConfig(taskConfig, aiConfig);

            if (taskConfig["eatSound"] != null)
            {
                string eatsoundstring = taskConfig["eatSound"].AsString(null);
                if (eatsoundstring != null)
                {
                    eatSound = new AssetLocation(eatsoundstring).WithPathPrefix("sounds/");
                }
            }

            if (taskConfig["movespeed"] != null)
            {
                moveSpeed = taskConfig["movespeed"].AsFloat(0.02f);
            }

            if (taskConfig["searchPlayerInv"] != null)
            {
                searchPlayerInv = taskConfig["searchPlayerInv"].AsBool(false);
            }

            if (taskConfig["eatTime"] != null)
            {
                eatTime = taskConfig["eatTime"].AsFloat(1.5f);
            }

            if (taskConfig["doConsumePortion"] != null)
            {
                doConsumePortion = taskConfig["doConsumePortion"].AsBool(true);
            }

            if (taskConfig["eatLooseItems"] != null)
            {
                eatLooseItems = taskConfig["eatLooseItems"].AsBool(true);
            }

            if (taskConfig["playEatAnimForLooseItems"] != null)
            {
                playEatAnimForLooseItems = taskConfig["playEatAnimForLooseItems"].AsBool(true);
            }

            if (taskConfig["eatItemCategories"] != null)
            {
                foreach (var val in taskConfig["eatItemCategories"].AsArray <EnumFoodCategory>(new EnumFoodCategory[0]))
                {
                    eatItemCategories.Add(val);
                }
            }

            if (taskConfig["eatItemCodes"] != null)
            {
                foreach (var val in taskConfig["eatItemCodes"].AsArray(new AssetLocation[0]))
                {
                    eatItemCodes.Add(val);
                }
            }

            if (taskConfig["eatAnimation"].Exists)
            {
                eatAnimMeta = new AnimationMetaData()
                {
                    Code           = taskConfig["eatAnimation"].AsString()?.ToLowerInvariant(),
                    Animation      = taskConfig["eatAnimation"].AsString()?.ToLowerInvariant(),
                    AnimationSpeed = taskConfig["eatAnimationSpeed"].AsFloat(1f)
                }.Init();
            }

            if (taskConfig["eatAnimationLooseItems"].Exists)
            {
                eatAnimMetaLooseItems = new AnimationMetaData()
                {
                    Code           = taskConfig["eatAnimationLooseItems"].AsString()?.ToLowerInvariant(),
                    Animation      = taskConfig["eatAnimationLooseItems"].AsString()?.ToLowerInvariant(),
                    AnimationSpeed = taskConfig["eatAnimationSpeedLooseItems"].AsFloat(1f)
                }.Init();
            }
        }
Exemplo n.º 21
0
 public static void PlaySoundAt(this IWorldAccessor world, AssetLocation loc, BlockPos Pos) => world.PlaySoundAt(loc, Pos.X, Pos.Y, Pos.Z);
Exemplo n.º 22
0
        public MeshData GetPieMesh(ItemStack pieStack, ModelTransform transform = null)
        {
            // Slot 0: Base dough
            // Slot 1: Filling
            // Slot 2: Crust dough

            nowTesselatingBlock = pieStack.Block as BlockPie;
            if (nowTesselatingBlock == null)
            {
                return(null);                              //This will occur if the pieStack changed to rot
            }
            contentStacks = nowTesselatingBlock.GetContents(capi.World, pieStack);

            int pieSize = pieStack.Attributes.GetInt("pieSize");


            // At this spot we have to determine the textures for "dough" and "filling"
            // Texture determination rules:
            // 1. dough is simple: first itemstack must be dough, take from attributes
            // 2. pie allows 4 items as fillings, but with specific mixing rules
            //    - berries/fruit can be mixed
            //    - vegetables can be mixed
            //    - meat can be mixed
            // no other mixing allowed

            // Thus we deduce: It's enough to test if
            // a) all 4 fillings are equal: Then use texture from inPieProperties from first one
            // b) Otherwise use hardcoded
            //    for item.NutritionProps.FoodCategory == Vegetable   => block/food/pie/fill-mixedvegetable.png
            //    for item.NutritionProps.FoodCategory == Protein   => block/food/pie/fill-mixedmeat.png
            //    for item.NutritionProps.FoodCategory == Fruit   => block/food/pie/fill-mixedfruit.png

            var stackprops = contentStacks.Select(stack => stack?.ItemAttributes?["inPieProperties"]?.AsObject <InPieProperties>(null, stack.Collectible.Code.Domain)).ToArray();

            int bakeLevel = pieStack.Attributes.GetInt("bakeLevel", 0);

            if (stackprops.Length == 0)
            {
                return(null);
            }


            ItemStack cstack = contentStacks[1];
            bool      equal  = true;

            for (int i = 2; equal && i < contentStacks.Length - 1; i++)
            {
                if (contentStacks[i] == null || cstack == null)
                {
                    continue;
                }

                equal &= cstack.Equals(capi.World, contentStacks[i], GlobalConstants.IgnoredStackAttributes);
                cstack = contentStacks[i];
            }


            if (ContentsRotten(contentStacks))
            {
                crustTextureLoc    = new AssetLocation("block/rot/rot");
                fillingTextureLoc  = new AssetLocation("block/rot/rot");
                topCrustTextureLoc = new AssetLocation("block/rot/rot");
            }
            else
            {
                if (stackprops[0] != null)
                {
                    crustTextureLoc      = stackprops[0].Texture.Clone();
                    crustTextureLoc.Path = crustTextureLoc.Path.Replace("{bakelevel}", "" + (bakeLevel + 1));
                    fillingTextureLoc    = new AssetLocation("block/transparent");
                }

                topCrustTextureLoc = new AssetLocation("block/transparent");
                if (stackprops[5] != null)
                {
                    topCrustTextureLoc      = stackprops[5].Texture.Clone();
                    topCrustTextureLoc.Path = topCrustTextureLoc.Path.Replace("{bakelevel}", "" + (bakeLevel + 1));
                }

                if (contentStacks[1] != null)
                {
                    EnumFoodCategory fillingFoodCat =
                        contentStacks[1].Collectible.NutritionProps?.FoodCategory
                        ?? contentStacks[1].ItemAttributes?["nutritionPropsWhenInMeal"]?.AsObject <FoodNutritionProperties>()?.FoodCategory
                        ?? EnumFoodCategory.Vegetable
                    ;

                    fillingTextureLoc = equal ? stackprops[1]?.Texture : pieMixedFillingTextures[(int)fillingFoodCat];
                }
            }


            int  fillLevel  = (contentStacks[1] != null ? 1 : 0) + (contentStacks[2] != null ? 1 : 0) + (contentStacks[3] != null ? 1 : 0) + (contentStacks[4] != null ? 1 : 0);
            bool isComplete = fillLevel == 4;

            AssetLocation shapeloc = isComplete ? pieShapeBySize[pieSize - 1] : pieShapeLocByFillLevel[fillLevel];

            shapeloc.WithPathAppendixOnce(".json").WithPathPrefixOnce("shapes/");
            Shape    shape = capi.Assets.TryGet(shapeloc).ToObject <Shape>();
            MeshData mesh;

            int topCrustType = pieStack.Attributes.GetInt("topCrustType");

            string[] topCrusts         = new string[] { "origin/base/top crust full/*", "origin/base/top crust square/*", "origin/base/top crust diagonal/*" };
            string[] selectiveElements = new string[] { "origin/base/crust regular/*", "origin/base/filling/*", "origin/base/base-quarter/*", "origin/base/fillingquarter/*", topCrusts[topCrustType] };

            capi.Tesselator.TesselateShape("pie", shape, out mesh, this, null, 0, 0, 0, null, selectiveElements);
            if (transform != null)
            {
                mesh.ModelTransform(transform);
            }

            return(mesh);
        }
Exemplo n.º 23
0
 public static ClothSystem CreateRope(ICoreAPI api, ClothManager cm, BlockPos originPos, float length, AssetLocation clothSectionModel)
 {
     return(new ClothSystem(api, cm, originPos, length, 0, EnumClothType.Rope, clothSectionModel));
 }
Exemplo n.º 24
0
        public MeshData GenFoodMixMesh(ItemStack[] contentStacks, CookingRecipe recipe, Vec3f foodTranslate)
        {
            MeshData          mergedmesh = null;
            MealTextureSource texSource  = new MealTextureSource(capi, mealtextureSourceBlock);

            var shapePath = recipe.Shape.Base.Clone().WithPathPrefixOnce("shapes/").WithPathAppendixOnce(".json");

            bool rotten = ContentsRotten(contentStacks);

            if (rotten)
            {
                shapePath = new AssetLocation("shapes/block/food/meal/rot.json");
            }

            Shape shape = capi.Assets.TryGet(shapePath).ToObject <Shape>();
            Dictionary <CookingRecipeIngredient, int> usedIngredQuantities = new Dictionary <CookingRecipeIngredient, int>();

            if (rotten)
            {
                capi.Tesselator.TesselateShape(
                    "mealpart", shape, out mergedmesh, texSource,
                    new Vec3f(recipe.Shape.rotateX, recipe.Shape.rotateY, recipe.Shape.rotateZ)
                    );
            }
            else
            {
                HashSet <string> drawnMeshes = new HashSet <string>();

                for (int i = 0; i < contentStacks.Length; i++)
                {
                    texSource.ForStack = contentStacks[i];
                    CookingRecipeIngredient ingred = recipe.GetIngrendientFor(
                        contentStacks[i],
                        usedIngredQuantities.Where(val => val.Key.MaxQuantity <= val.Value).Select(val => val.Key).ToArray()
                        );

                    if (ingred == null)
                    {
                        ingred = recipe.GetIngrendientFor(contentStacks[i]);
                    }
                    else
                    {
                        int cnt = 0;
                        usedIngredQuantities.TryGetValue(ingred, out cnt);
                        cnt++;
                        usedIngredQuantities[ingred] = cnt;
                    }

                    if (ingred == null)
                    {
                        continue;
                    }


                    MeshData meshpart;
                    string[] selectiveElements = null;

                    CookingRecipeStack recipestack = ingred.GetMatchingStack(contentStacks[i]);

                    if (recipestack.ShapeElement != null)
                    {
                        selectiveElements = new string[] { recipestack.ShapeElement }
                    }
                    ;
                    texSource.customTextureMapping = recipestack.TextureMapping;

                    if (drawnMeshes.Contains(recipestack.ShapeElement + recipestack.TextureMapping))
                    {
                        continue;
                    }
                    drawnMeshes.Add(recipestack.ShapeElement + recipestack.TextureMapping);

                    capi.Tesselator.TesselateShape(
                        "mealpart", shape, out meshpart, texSource,
                        new Vec3f(recipe.Shape.rotateX, recipe.Shape.rotateY, recipe.Shape.rotateZ), 0, 0, 0, null, selectiveElements
                        );

                    if (mergedmesh == null)
                    {
                        mergedmesh = meshpart;
                    }
                    else
                    {
                        mergedmesh.AddMeshData(meshpart);
                    }
                }
            }


            if (foodTranslate != null && mergedmesh != null)
            {
                mergedmesh.Translate(foodTranslate);
            }

            return(mergedmesh);
        }
Exemplo n.º 25
0
        public EntityBlockFalling(Block block, BlockEntity blockEntity, BlockPos initialPos, AssetLocation fallSound, float impactDamageMul, bool canFallSideways, bool dustyFall)
        {
            this.impactDamageMul = impactDamageMul;
            this.fallSound       = fallSound;
            this.canFallSideways = canFallSideways;
            this.dustyFall       = dustyFall;

            WatchedAttributes.SetBool("canFallSideways", canFallSideways);
            WatchedAttributes.SetBool("dustyFall", dustyFall);
            if (fallSound != null)
            {
                WatchedAttributes.SetString("fallSound", fallSound.ToShortString());
            }

            this.Code               = new AssetLocation("blockfalling");
            this.blockCode          = block.Code;
            this.removedBlockentity = blockEntity;
            this.initialPos         = initialPos;

            ServerPos.SetPos(initialPos);
            ServerPos.X += 0.5;
            ServerPos.Z += 0.5;

            Pos.SetFrom(ServerPos);
        }
Exemplo n.º 26
0
        public static bool WildCardMatches(AssetLocation blockCode, List <AssetLocation> wildCards, out AssetLocation matchingWildcard)
        {
            foreach (AssetLocation wildcard in wildCards)
            {
                if (WildCardMatch(wildcard, blockCode))
                {
                    matchingWildcard = wildcard;
                    return(true);
                }
            }

            matchingWildcard = null;

            return(false);
        }
Exemplo n.º 27
0
 public static Block GetBlock(this AssetLocation asset, ICoreAPI api)
 {
     return(api.World.BlockAccessor.GetBlock(asset));
 }
Exemplo n.º 28
0
        public override void LoadConfig(JsonObject taskConfig, JsonObject aiConfig)
        {
            partitionUtil = entity.Api.ModLoader.GetModSystem <EntityPartitioning>();

            this.minduration = taskConfig["minduration"].AsInt(2000);
            this.maxduration = taskConfig["maxduration"].AsInt(4000);
            this.chance      = taskConfig["chance"].AsFloat(1.1f);
            string code = taskConfig["onBlockBelowCode"].AsString(null);

            if (code != null && code.Length > 0)
            {
                this.onBlockBelowCode = new AssetLocation(code);
            }

            if (taskConfig["stopRange"] != null)
            {
                stopRange = taskConfig["stopRange"].AsFloat(0f);
            }

            if (taskConfig["stopOnHurt"] != null)
            {
                stopOnHurt = taskConfig["stopOnHurt"].AsBool(false);
            }

            if (taskConfig["duringDayTimeFrames"] != null)
            {
                duringDayTimeFrames = taskConfig["duringDayTimeFrames"].AsObject <DayTimeFrame[]>(null);
            }

            if (taskConfig["stopOnNearbyEntityCodes"] != null)
            {
                string[] codes = taskConfig["stopOnNearbyEntityCodes"].AsArray <string>(new string[] { "player" });

                List <string> exact      = new List <string>();
                List <string> beginswith = new List <string>();

                for (int i = 0; i < codes.Length; i++)
                {
                    string ecode = codes[i];
                    if (ecode.EndsWith("*"))
                    {
                        beginswith.Add(ecode.Substring(0, ecode.Length - 1));
                    }
                    else
                    {
                        exact.Add(ecode);
                    }
                }

                stopOnNearbyEntityCodesExact      = exact.ToArray();
                stopOnNearbyEntityCodesBeginsWith = beginswith.ToArray();
            }



            idleUntilMs = entity.World.ElapsedMilliseconds + minduration + entity.World.Rand.Next(maxduration - minduration);

            int   generation          = entity.WatchedAttributes.GetInt("generation", 0);
            float fearReductionFactor = Math.Max(0f, (10f - generation) / 10f);

            if (whenInEmotionState != null)
            {
                fearReductionFactor = 1;
            }

            stopRange *= fearReductionFactor;

            base.LoadConfig(taskConfig, aiConfig);
        }
Exemplo n.º 29
0
 public static void PlaySoundAtWithDelay(this IWorldAccessor world, AssetLocation location, BlockPos pos, int delay)
 {
     world.RegisterCallback(dt => world.PlaySoundAt(location, pos.X, pos.Y, pos.Z), delay);
 }
Exemplo n.º 30
0
        public override void OnBlockInteractStop(float secondsUsed, IWorldAccessor world, IPlayer byPlayer, BlockSelection blockSel, ref EnumHandling handling)
        {
            BlockPos Pos = blockSel?.Position;

            if (Pos == null)
            {
                return;
            }

            ModSystemBlockReinforcement bR = Api.ModLoader.GetModSystem <ModSystemBlockReinforcement>();

            if (disabled || bR.IsReinforced(Pos) || bR.IsLockedForInteract(Pos, byPlayer))
            {
                return;
            }

            SwapSystem swapSystem = Api.ModLoader.GetModSystem <SwapSystem>();

            handling = EnumHandling.PreventDefault;
            ItemSlot slot = byPlayer.InventoryManager.ActiveHotbarSlot;


            if (!(requireSneak && !byPlayer.Entity.Controls.Sneak) && slot.Itemstack != null)
            {
                string key = GetKey(slot.Itemstack.Collectible.Code.ToString());

                if (swapSystem.SwapPairs.TryGetValue(key, out SwapBlocks swap))
                {
                    if (world.Side.IsClient())
                    {
                        Api.ModLoader.GetModSystem <ShaderTest>().progressBar = 0;
                    }

                    if (swap.Takes != null && swap.Takes != block.Code.ToString() || secondsUsed < swap.MakeTime)
                    {
                        return;
                    }

                    AssetLocation asset = slot.Itemstack.Collectible.Code;
                    if (asset.ToString() == swap.Tool)
                    {
                        AssetLocation toAsset = new AssetLocation(swap.Makes.WithDomain());
                        Block         toBlock = toAsset.GetBlock(world.Api);

                        int count = swap.Count;

                        if (count != 0)
                        {
                            if (count < 0)
                            {
                                ItemStack withCount = slot.Itemstack.Clone();
                                withCount.StackSize = Math.Abs(count);
                                if (!byPlayer.InventoryManager.TryGiveItemstack(withCount))
                                {
                                    world.SpawnItemEntity(withCount, Pos.ToVec3d().Add(0.5, 0.5, 0.5));
                                }
                            }
                            else if (slot.Itemstack.StackSize >= count)
                            {
                                if (byPlayer.WorldData.CurrentGameMode.IsSurvival())
                                {
                                    slot.TakeOut(count);
                                }
                            }
                            else
                            {
                                return;
                            }
                        }

                        if ((block.EntityClass != null && toBlock.EntityClass != null) && (toBlock.EntityClass == block.EntityClass))
                        {
                            world.BlockAccessor.ExchangeBlock(toBlock.BlockId, Pos);
                        }
                        else
                        {
                            world.BlockAccessor.SetBlock(toBlock.BlockId, Pos);
                        }
                        slot.MarkDirty();
                        PlaySoundDispenseParticles(world, Pos, slot);
                        return;
                    }
                }
            }

            ItemStack stack = byPlayer?.InventoryManager?.ActiveHotbarSlot?.Itemstack;

            if (stack != null && allowPlaceOn)
            {
                string         r      = "";
                BlockSelection newsel = blockSel.Clone();
                newsel.Position = newsel.Position.Offset(blockSel.Face);
                Block block = stack.Block;

                if (block != null && block.TryPlaceBlock(world, byPlayer, stack, newsel, ref r))
                {
                    world.PlaySoundAt(stack.Block?.Sounds.Place, newsel.Position);
                }
            }
        }
Exemplo n.º 31
0
 public AssetTag(AssetType assetType, string name, AssetLocation[] assetLocations)
 {
     AssetType = assetType;
     Name = name;
     AssetLocations = assetLocations;
 }
Exemplo n.º 32
0
 public AssetWithLocationModel(Asset asset, AssetLocation location, bool isUserAuthenticated = false) :
     base(asset, isUserAuthenticated)
 {
     this.Location = location;
     Location.IgnoreAssetId = true;
 }