minetest / minetest

Minetest is an open source voxel game-creation platform with easy modding and game creation
https://www.minetest.net/
Other
10.57k stars 2k forks source link

Use metadata in schematic placed nodes #5263

Open MarkuBu opened 7 years ago

MarkuBu commented 7 years ago

I want to be able to place simple schematics like small buildings, which includes nodes like chests and furnaces. Currently I can place them, but they don't work.

I propose to add metadata to schematics because this has a lot of potential to add more gameplay features. Also I propose that the metadata can be modified before place the (lua) schematic.

Just an example:

local ch = { name = "default:chest", meta = {"something"}, inv = {"default:picaxe", "default:apple 10"} }

or something like that

sfan5 commented 7 years ago

If you are using Lua anyway then it's trivial to manually add metadata after placing the nodes.

paramat commented 7 years ago

~-1 Also, schematics are lacking this ability because they are meant to be fast.~

rubenwardy commented 4 years ago

I support this feature. I've had to work around this on 3 of the major projects I've been involved in: CTF, QiskitBlocks, and Craft the Web.

-1 Also, schematics are lacking this ability because they are meant to be fast.

Adding metadata doesn't mean that it needs to be slow. Metadata is usually done in a footer, if there is no footer then it is skipped

If you are using Lua anyway then it's trivial to manually add metadata after placing the nodes.

It is not trivial, it requires a fairly large amount of custom code which is inefficient due to Lua not having the ability to know whether metadata exists at a certain location. Here is an implementation I made: https://github.com/JavaFXpert/QiskitBlocks/blob/master/qiskitblocks/mods/xschem/api.lua

LoneWolfHT commented 4 years ago

I'm working on a game that could really use this :+1:

paramat commented 4 years ago

It seems wrong to me to have the metadata data in the schematic itself, as a schematic is meant to contain node data only. Metadata is verbose so seems out of place in the super-compact schematic node data.

If a schematic itself contains the metadata then it becomes far less flexible because (for example) every 'house with chest' will have a chest containing exactly the same items. It seems very likely that a modder will want to use a single house schematic but be free to alter the items in the chest. Otherwise they would have to create multple house schematics for every variation chest contents.

So it seems better to handling, and define, the metadata in the fields of the 'place schematic' API and the decoration definition API. The 'place schematic' API already has a field for 'replacements', metadata seems to belong together with that.

The first post proposes:

Also I propose that the metadata can be modified before place the (lua) schematic.

Which is related to my suggestion, however, if it can be modified in the API then it might as well be defined there, keeping the implementation simpler.

~So i am -1 for 'adding metadata to schematic files', but no objection to setting it in the API that actually places a schematic or defines a decoration.~

EDIT: Not sure now. It may be best to allow metadata in the schematic itself, but also allow it to be set independently. Whatever happens, there needs to be an option for it to be independent.

LoneWolfHT commented 4 years ago

If a schematic itself contains the metadata then it becomes far less flexible because (for example) every 'house with chest' will have a chest containing exactly the same items. It seems very likely that a modder will want to use a single house schematic but be free to alter the items in the chest. Otherwise they would have to create multple house schematics for every variation chest contents.

In this case I would empty the chest(s) before saving the schematic and once the schematic was placed I would find all chest nodes inside the area and then modify their inventory to my liking.

A setting to allow for the ignoring of metadata when saving (and possibly placing) a schematic might be nice, for modders who don't need to use it # One of my use-cases for this is saving a town schematic containing NPCs. The NPCs would be placed as nodes by the builder, with their metadata being used to set up special attributes like dialog, weapons, armor, skin-related things, etc. The builder would be able to change this all via a formspec that pops up upon rightclicking the NPC node. When the schematic is placed all of the NPC nodes would be 'converted' into entity form by a LBM or something similar. The node's metadata would then be moved into the entity.

LoneWolfHT commented 4 years ago

A setting to allow for the ignoring of metadata when saving (and possibly placing) a schematic might be nice, for modders who don't need to use it

I think this would be really useful for modders who don't want to worry about accidentally saving metadata. So full support for this

benrob0329 commented 4 years ago

If a schematic itself contains the metadata then it becomes far less flexible because (for example) every 'house with chest' will have a chest containing exactly the same items.

I don't use *.mts schematics, but rather build table schematics in code for my game so this point does not apply to every use-case, as I could easily change the metadata in the schematic. I also would benefit from the feature, because as of right now I manually set the metadata for roughly 320 nodes per mapblock (8 racks per block, they're 2 blocks wide and 4 blocks long so 64 floor positions, then stack 5 per floor space because shelves) and while I haven't seen a degradation in performance, I'm sure low-powered servers would be happier if this could be done in bulk.

paramat commented 4 years ago

LoneWolfHT,

In this case I would empty the chest(s) before saving the schematic and once the schematic was placed I would find all chest nodes inside the area and then modify their inventory to my liking.

Ok. But, it would be simpler for you, and for MT, to not do this in 2 steps, but just do it all using a field in the schematic-placing API, as i suggest. Besides, you are focussing on an example, i was using that example to make a general point: Metadata in schematics is very inflexible, and metadata in schematics will usually be required to be independent of a schematic.

benrob0329,

I don't use *.mts schematics, but rather build table schematics in code for my game so this point does not apply to every use-case, as I could easily change the metadata in the schematic

This feature request is for .mts schematics, so i was obviously referring to .mts schematics, any other implementation of schematics is irrelevant to my point.

////////////////////////////////

Looking at the fields of schematic-placing APIs:

    // place_schematic(p, schematic, rotation,
    //     replacements, force_placement, flagstring)
    static int l_place_schematic(lua_State *L);

    // place_schematic_on_vmanip(vm, p, schematic, rotation,
    //     replacements, force_placement, flagstring)
    static int l_place_schematic_on_vmanip(lua_State *L);

Schematic decorations:

        ----- Schematic-type parameters

        schematic = "foobar.mts",
        -- If schematic is a string, it is the filepath relative to the current
        -- working directory of the specified Minetest schematic file.
        -- Could also be the ID of a previously registered schematic.

        schematic = {
            size = {x = 4, y = 6, z = 4},
            data = {
                {name = "default:cobble", param1 = 255, param2 = 0},
                {name = "default:dirt_with_grass", param1 = 255, param2 = 0},
                {name = "air", param1 = 255, param2 = 0},
                 ...
            },
            yslice_prob = {
                {ypos = 2, prob = 128},
                {ypos = 5, prob = 64},
                 ...
            },
        },
        -- Alternative schematic specification by supplying a table. The fields
        -- size and data are mandatory whereas yslice_prob is optional.
        -- See 'Schematic specifier' for details.

        replacements = {["oldname"] = "convert_to", ...},

        flags = "place_center_x, place_center_y, place_center_z",
        -- Flags for schematic decorations. See 'Schematic attributes'.

        rotation = "90",
        -- Rotation can be "0", "90", "180", "270", or "random"

        place_offset_y = 0,
        -- If the flag 'place_center_y' is set this parameter is ignored.
        -- Y offset of the schematic base node layer relative to the 'place_on'
        -- node.
        -- Can be positive or negative. Default is 0.
        -- Effect is inverted for "all_ceilings" decorations.
        -- Ignored by 'y_min', 'y_max' and 'spawn_by' checks, which always refer
        -- to the 'place_on' node.
    }

The basic node ID and node rotation data is in the schematic. All more specialist and less node-related data is set in the fields of the API. Metadata is certainly more specialist and less node-related data, so clearly should not be in the schematic file. Doing so also makes it flexible, as will be required for most usage.

rubenwardy commented 4 years ago

Metadata is not specialist and is completely node-related

LoneWolfHT commented 4 years ago

Ok. But, it would be simpler for you, and for MT, to not do this in 2 steps, but just do it all using a field in the schematic-placing API, as i suggest.

I'd be fine with doing that. My point was that in your example you could just ignore the metadata, since you wouldn't really need it in that case. In my case the metadata has to be decided when the schematic is saved, not loaded. So fields in the schematic-placing API won't help me unless I save all the metadata in a separate file and load it from there every time I place the schematic, which would be a pain to do and basically equivalent to writing my own mini schematic API.

benrob0329 commented 4 years ago

This feature request is for .mts schematics

Actually, the OP never mentioned what kind of schematics they were referring to, and not having feature parody between the two kinds would be a severe oversight IMO.

ClobberXD commented 4 years ago

I support this feature request, this feature needs to exist as an option while creating schematics. Makes life so much easier for those who use all sorts of wanky hacks to workaround this short-coming.

Prime use-cases are CTF, ITB, and other games that use pre-saved regions as schematics. It's for this shortcoming that CTF doesn't allow nodes that require meta in maps. If node meta could be saved too, maps can use a much larger variety of nodes, including pre-filled chests, signs, steel doors, etc. Here's an example use-case - I was strongly contemplating on adding support for pre-filled chests in maps at a certain point in time. Here's the relevant feature request. Notice how needlessly complex the implementation needs to be (for no good reason):

separate file ... that stores the contents of each node-inv in a comma-separated itemstring form, with pos of the chest being the key.

If this feature request is implemented, pre-filled chests would work out of the box, without the need for any extra hacks.

ITB also requires heavy use of node meta, and has to resort to a custom file format, containing "manually" (via code) serialised node data and node metas for all nodes included.

It seems wrong to me to have the metadata data in the schematic itself, as a schematic is meant to contain node data only. Metadata is verbose so seems out of place in the super-compact schematic node data.

Then we could use a separate file, like <filename>.mts.meta. Schem-placing API methods would automatically look for, and parse this auxillliary file, unless maybe explicitly specified not to.

paramat commented 4 years ago

Metadata is not specialist and is completely node-related

You are missing my point and are misrepresenting what i wrote. I wrote 'more specialist and less node-related', the words 'more' and 'less' were added to make clear i am not saying metadata is very specialist, and am not saying it is node-unrelated. I added those words specifically to try to avoid the exact response you made.

'more specialist and less node-related' means the things less related to basic node ID/rotation/probability, it means aspects like the other fields in the APIs. Metadata is somewhat specialist because the vast majority of schematics used in MT do not involve metadata (all the tree schmatics).

benrob0329, sorry i misunderstood, you meant engine-supported lua table schematics, i thought you were referring to your own personal implementation of schematics. No wonder i was confused. Good point too, whether the metadata should be included in the lua table schematic itself.

Anyway to be clear, i do not object to the feature (i removed my earlier -1).

benrob0329 commented 4 years ago

For the Table-Schematic support, perhaps node tables ({name = "node:name", param1 = 255, param2 = 0}) could be expanded to have an optional "meta" field.