1. Hey Guest, is it this your first time on the forums?

    Visit the Beginner's Box

    Introduce yourself, read some of the ins and outs of the community, access to useful links and information.

    Dismiss Notice

Custom tiles (not blobs)

Discussion in 'Modding Help' started by sinitreo, May 2, 2014.

  1. sinitreo

    sinitreo Shopkeep Stealer
    1. Zen Laboratories

    Messages:
    66
    Is there any possibility that developers will add a way to extend current tile set?
    Even one of those features would greatly help customize the setting:
    - tiles that react to team palette
    - ability to use free space in world.png to define custom tile graphics and hit sound, yet have standard stone/wood physics.

    @Geti
     
    Blubahub and Crabmaster like this.
  2. Geti

    Geti Please avoid PMing me (poke a mod instead) THD Team Administrator Global Moderator

    Messages:
    3,730
    There's an example mod that already does most of the second one. MM still wants to add examples of setting, hitting, etc with custom tiles, but the required functionality is already in there.
    There's no "magic" logic that defines a tile, its "hit" graphics and its hit sound, there's just a function that hits a tile, and this changes it to a damaged tile (eg tile_ground to tile_ground_d1 ).

    We've talked about potentially adding this kind of functionality but it would really limit what you can do with tiles; as it is you can define your own custom hitting effects based on hitter, damage, who hit you, etc. You just have to make sure that anything that needs to interact with these custom tiles uses your custom tile hitting function.

    Perhaps a hook to control the hit tile logic would be best?



    The first one (team palette) unfortunately isn't possible in the tilemap code; that's why we had red doors in there separately. This is due to rendering speed concerns; if the tiles all use the same texture, they can be rendered much, much faster than if they use multiple textures. If you need team palette adjustments then use blobs, like the vanilla doors.
     
  3. sinitreo

    sinitreo Shopkeep Stealer
    1. Zen Laboratories

    Messages:
    66
    Thanks for the reply!

    Indeed, seems like most of features are there.

    Code:
    Perhaps a hook to control the hit tile logic would be best?
    It's good that I can define different sounds of hitting from different sources (tile hit handling per blob). But for graphics, I would prefer one centralized hook. Probably, combination of those would be great.

    Does it refer to physics and collapses?

    Because I cannot make my block solid currently. =(
    I can draw the tile, I can potentially add some hit sounds and change it's sprite to damaged one, but it still appears to be air block after all, since my character just falls through.

    So I tried to copy the pure solid stone wall block and just change it's type.
    My current test code is
    Code:
    CMap@ map = getMap();
    Tile t = map.getTileFromTileSpace(Vec2f(x,y));
    t.type = 233;
    map.server_SetTile(getMap().getTileWorldPosition(Vec2f(u,v)), t);
    
    Where x,y are the coordinates of standard non-damaged foreground stone wall block of type 48, built by a builder
    And u,v are coordinates for target block.

    I end up with a character just falling through. I have not done any tests about lightning or water passes, might be a problem too.
    I have also tried to set up tile flags manually. (COLLISION + SOLID)

    Is there anything else I miss?
     
  4. Geti

    Geti Please avoid PMing me (poke a mod instead) THD Team Administrator Global Moderator

    Messages:
    3,730
    As you've seen I'm sure, this is how the tile is set in the example tile mod.
    No need to touch the "Tile" object itself.
    Code:
    namespace CMap
    {
       enum CustomTiles
       {
         tile_goo = 256
       };
    };
    
    //....
    
    //setting the tile
    if (pixel == color_goo){
            map.SetTile(offset, CMap::tile_goo );
            map.AddTileFlag( offset, Tile::SOLID | Tile::COLLISION ); //solid and collision flags
    
            //map.AddTileFlag( offset, Tile::BACKGROUND );
            //map.AddTileFlag( offset, Tile::LADDER );
            //map.AddTileFlag( offset, Tile::LIGHT_PASSES );
            //map.AddTileFlag( offset, Tile::WATER_PASSES );
            //map.AddTileFlag( offset, Tile::FLAMMABLE );
            //map.AddTileFlag( offset, Tile::PLATFORM );
            //map.AddTileFlag( offset, Tile::LIGHT_SOURCE );
        }
    Note that you have to handle setting and unsetting the flags carefully yourself.

    I'll see what we can do about this.
     
  5. sinitreo

    sinitreo Shopkeep Stealer
    1. Zen Laboratories

    Messages:
    66
    Interesting.
    The code above works flawlessly. However it fails if I do this in the RCON console (\n added for readability):
    Code:
    CMap@ map = getMap();
    int16 offset = map.getTileOffsetFromTileSpace(Vec2f(30,30));
    map.SetTile(offset, 256); //256 = CMap::goo
    map.AddTileFlag(offset, Tile::SOLID | Tile::COLLISION | Tile::LIGHT_SOURCE );
    
    First thing I thought is that I perform this server-side so I should use server_SetTile

    Code:
    CMap@ map = getMap();int16 offset = map.getTileOffsetFromTileSpace(Vec2f(30,30));
    map.server_SetTile(map.getTileWorldPosition(Vec2f(30,30)), 256);
    map.AddTileFlag(offset, Tile::SOLID | Tile::COLLISION );
    
    And the result is quite interesting.
    On the picture below, you can see that:
    1. Tile visually appears
    2. Client considers it non-solid (grapplehook goes through)
    3. Server consideres it solid ( arrows are processed (almost) correctly)

    [​IMG]

    I was looking for a way to sync flags as well, but failed.
    Vanilla stone and wood have their flags set automatically when server_SetTile is called. Thus - vanilla building system works.
    But how would I do it with the custom block? Or am I completely missing the point?
     
    Last edited: May 5, 2014
  6. Geti

    Geti Please avoid PMing me (poke a mod instead) THD Team Administrator Global Moderator

    Messages:
    3,730
    At the moment, that's the issue - you can't do it without using commands in rules or something to set the tile flags properly on client.

    These are the flags I'm currently thinking would solve the issue

    Code:
    void server_onTileHit( CMap@ this, f32 damage, u16 &in oldTileType, u16 &out newTileType ); //newTileType is "set" as the type if its not 0xffff
    void onSetTile( CMap@ this, u16 tileType ); //for setting flags, server and client
    That'd be enough to respond to hits and respond to any server_SetTile stuff (the client would get the flags set too).
     
    Asu likes this.
  7. sinitreo

    sinitreo Shopkeep Stealer
    1. Zen Laboratories

    Messages:
    66
    This is awesome. OnSetTile would provide even more flexibility! Once you set, dirt you can use this hook on the client to set up flags properly and on the server you can place some random content around the block, like grass or bushes. Nice idea, Geti!