Make stairs work
This commit is contained in:
@@ -1,7 +1,7 @@
|
|||||||
{
|
{
|
||||||
"tiles": [
|
"tiles": [
|
||||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
0, 2, 2, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
0, 5, 5, 5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
@@ -17,7 +17,6 @@
|
|||||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
|
|
||||||
|
|
||||||
1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||||
|
|||||||
@@ -76,20 +76,43 @@ void entityWalk(entity_t *entity, const entitydir_t direction) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Get tile under foot
|
// Get tile under foot
|
||||||
tile_t tile = mapGetTile(newPos);
|
tile_t tileCurrent = mapGetTile(entity->position);
|
||||||
if(tile == TILE_NULL && newPos.z > 0) {
|
tile_t tileNew = mapGetTile(newPos);
|
||||||
// Check one level down for walkable tile (stairs down)
|
bool_t fall = false;
|
||||||
|
bool_t raise = false;
|
||||||
|
|
||||||
|
// Are we walking up stairs?
|
||||||
|
if(
|
||||||
|
tileIsStairs(tileCurrent) &&
|
||||||
|
(direction+TILE_STAIRS_SOUTH) == tileCurrent &&
|
||||||
|
newPos.z < (MAP_CHUNK_DEPTH - 1)
|
||||||
|
) {
|
||||||
|
tileNew = TILE_NULL;// Force check for stairs above.
|
||||||
|
worldpos_t abovePos = newPos;
|
||||||
|
abovePos.z += 1;
|
||||||
|
tile_t tileAbove = mapGetTile(abovePos);
|
||||||
|
|
||||||
|
if(tileAbove != TILE_NULL && tileIsWalkable(tileAbove)) {
|
||||||
|
// We can go up the stairs.
|
||||||
|
raise = true;
|
||||||
|
}
|
||||||
|
} else if(tileNew == TILE_NULL && newPos.z > 0) {
|
||||||
|
// Falling down?
|
||||||
worldpos_t belowPos = newPos;
|
worldpos_t belowPos = newPos;
|
||||||
belowPos.z -= 1;
|
belowPos.z -= 1;
|
||||||
tile_t belowTile = mapGetTile(belowPos);
|
tile_t tileBelow = mapGetTile(belowPos);
|
||||||
|
if(
|
||||||
if(belowTile == TILE_STAIRS_UP) {
|
tileBelow != TILE_NULL &&
|
||||||
tile = TILE_STAIRS_DOWN;// Mark current as stairs down
|
tileIsStairs(tileBelow) &&
|
||||||
|
(entityDirGetOpposite(direction)+TILE_STAIRS_SOUTH) == tileBelow
|
||||||
|
) {
|
||||||
|
// We will fall to this tile.
|
||||||
|
fall = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Tile walkable?
|
// Can we walk here?
|
||||||
if(!tileIsWalkable(tile)) return;
|
if(!raise && !fall && !tileIsWalkable(tileNew)) return;// Blocked
|
||||||
|
|
||||||
// Entity in way?
|
// Entity in way?
|
||||||
entity_t *other = ENTITIES;
|
entity_t *other = ENTITIES;
|
||||||
@@ -105,13 +128,10 @@ void entityWalk(entity_t *entity, const entitydir_t direction) {
|
|||||||
entity->animation = ENTITY_ANIM_WALK;
|
entity->animation = ENTITY_ANIM_WALK;
|
||||||
entity->animTime = ENTITY_ANIM_WALK_DURATION;// TODO: Running vs walking
|
entity->animTime = ENTITY_ANIM_WALK_DURATION;// TODO: Running vs walking
|
||||||
|
|
||||||
// We are comitting, we can run effects here.
|
if(raise) {
|
||||||
if(tile == TILE_STAIRS_DOWN) {
|
|
||||||
// Moving down a level
|
|
||||||
entity->position.z -= 1;
|
|
||||||
} else if(tile == TILE_STAIRS_UP) {
|
|
||||||
// Moving up a level
|
|
||||||
entity->position.z += 1;
|
entity->position.z += 1;
|
||||||
|
} else if(fall) {
|
||||||
|
entity->position.z -= 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -8,6 +8,16 @@
|
|||||||
#include "entitydir.h"
|
#include "entitydir.h"
|
||||||
#include "assert/assert.h"
|
#include "assert/assert.h"
|
||||||
|
|
||||||
|
entitydir_t entityDirGetOpposite(const entitydir_t dir) {
|
||||||
|
switch(dir) {
|
||||||
|
case ENTITY_DIR_NORTH: return ENTITY_DIR_SOUTH;
|
||||||
|
case ENTITY_DIR_SOUTH: return ENTITY_DIR_NORTH;
|
||||||
|
case ENTITY_DIR_EAST: return ENTITY_DIR_WEST;
|
||||||
|
case ENTITY_DIR_WEST: return ENTITY_DIR_EAST;
|
||||||
|
default: return dir;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void entityDirGetRelative(
|
void entityDirGetRelative(
|
||||||
const entitydir_t from,
|
const entitydir_t from,
|
||||||
worldunits_t *outX,
|
worldunits_t *outX,
|
||||||
|
|||||||
@@ -20,6 +20,14 @@ typedef enum {
|
|||||||
ENTITY_DIR_RIGHT = ENTITY_DIR_EAST,
|
ENTITY_DIR_RIGHT = ENTITY_DIR_EAST,
|
||||||
} entitydir_t;
|
} entitydir_t;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the opposite direction of a given direction.
|
||||||
|
*
|
||||||
|
* @param dir The direction to get the opposite of.
|
||||||
|
* @return entitydir_t The opposite direction.
|
||||||
|
*/
|
||||||
|
entitydir_t entityDirGetOpposite(const entitydir_t dir);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Asserts a given direction is valid.
|
* Asserts a given direction is valid.
|
||||||
*
|
*
|
||||||
|
|||||||
@@ -8,10 +8,10 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
#include "rpg/world/tile.h"
|
#include "rpg/world/tile.h"
|
||||||
#include "worldpos.h"
|
#include "worldpos.h"
|
||||||
#include "display/mesh/mesh.h"
|
#include "display/mesh/quad.h"
|
||||||
|
|
||||||
#define CHUNK_VERTEX_COUNT_MAX (6 * CHUNK_TILE_COUNT * 2)
|
#define CHUNK_VERTEX_COUNT_MAX (QUAD_VERTEX_COUNT * CHUNK_TILE_COUNT * 2)
|
||||||
#define CHUNK_MESH_COUNT_MAX 12
|
#define CHUNK_MESH_COUNT_MAX 14
|
||||||
|
|
||||||
typedef struct chunk_s {
|
typedef struct chunk_s {
|
||||||
chunkpos_t position;
|
chunkpos_t position;
|
||||||
|
|||||||
@@ -1,14 +0,0 @@
|
|||||||
/**
|
|
||||||
* Copyright (c) 2025 Dominic Masters
|
|
||||||
*
|
|
||||||
* This software is released under the MIT License.
|
|
||||||
* https://opensource.org/licenses/MIT
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
#include "dusk.h"
|
|
||||||
|
|
||||||
typedef struct {
|
|
||||||
vec2 min;
|
|
||||||
vec2 max;
|
|
||||||
} region_t;
|
|
||||||
@@ -8,9 +8,28 @@
|
|||||||
#include "tile.h"
|
#include "tile.h"
|
||||||
|
|
||||||
bool_t tileIsWalkable(const tile_t tile) {
|
bool_t tileIsWalkable(const tile_t tile) {
|
||||||
return (
|
switch(tile) {
|
||||||
tile == TILE_WALKABLE ||
|
case TILE_WALKABLE:
|
||||||
tile == TILE_STAIRS_UP ||
|
case TILE_STAIRS_NORTH:
|
||||||
tile == TILE_STAIRS_DOWN
|
case TILE_STAIRS_SOUTH:
|
||||||
);
|
case TILE_STAIRS_EAST:
|
||||||
|
case TILE_STAIRS_WEST:
|
||||||
|
return true;
|
||||||
|
|
||||||
|
default:
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
bool_t tileIsStairs(const tile_t tile) {
|
||||||
|
switch(tile) {
|
||||||
|
case TILE_STAIRS_NORTH:
|
||||||
|
case TILE_STAIRS_SOUTH:
|
||||||
|
case TILE_STAIRS_EAST:
|
||||||
|
case TILE_STAIRS_WEST:
|
||||||
|
return true;
|
||||||
|
|
||||||
|
default:
|
||||||
|
return false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
@@ -6,15 +6,18 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
#pragma once
|
#pragma once
|
||||||
#include "dusk.h"
|
#include "rpg/entity/entitydir.h"
|
||||||
|
|
||||||
|
|
||||||
typedef uint8_t tile_t;
|
typedef uint8_t tile_t;
|
||||||
|
|
||||||
#define TILE_NULL 0
|
#define TILE_NULL 0
|
||||||
#define TILE_WALKABLE 1
|
#define TILE_WALKABLE 1
|
||||||
#define TILE_STAIRS_UP 2
|
#define TILE_STAIRS_SOUTH (2 + ENTITY_DIR_SOUTH)
|
||||||
#define TILE_STAIRS_DOWN 3
|
#define TILE_STAIRS_EAST (2 + ENTITY_DIR_EAST)
|
||||||
|
#define TILE_STAIRS_WEST (2 + ENTITY_DIR_WEST)
|
||||||
|
#define TILE_STAIRS_NORTH (2 + ENTITY_DIR_NORTH)
|
||||||
|
#define TILE_TEST 6
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns whether or not the given tile is walkable.
|
* Returns whether or not the given tile is walkable.
|
||||||
@@ -23,3 +26,11 @@ typedef uint8_t tile_t;
|
|||||||
* @return bool_t True if walkable, false if not.
|
* @return bool_t True if walkable, false if not.
|
||||||
*/
|
*/
|
||||||
bool_t tileIsWalkable(const tile_t tile);
|
bool_t tileIsWalkable(const tile_t tile);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns whether or not the given tile is a stairs tile.
|
||||||
|
*
|
||||||
|
* @param tile The tile to check.
|
||||||
|
* @return bool_t True if stairs, false if not.
|
||||||
|
*/
|
||||||
|
bool_t tileIsStairs(const tile_t tile);
|
||||||
@@ -10,7 +10,7 @@
|
|||||||
|
|
||||||
#define CHUNK_WIDTH 16
|
#define CHUNK_WIDTH 16
|
||||||
#define CHUNK_HEIGHT 16
|
#define CHUNK_HEIGHT 16
|
||||||
#define CHUNK_DEPTH 8
|
#define CHUNK_DEPTH 4
|
||||||
#define CHUNK_TILE_COUNT (CHUNK_WIDTH * CHUNK_HEIGHT * CHUNK_DEPTH)
|
#define CHUNK_TILE_COUNT (CHUNK_WIDTH * CHUNK_HEIGHT * CHUNK_DEPTH)
|
||||||
|
|
||||||
#define MAP_CHUNK_WIDTH 3
|
#define MAP_CHUNK_WIDTH 3
|
||||||
|
|||||||
@@ -8,7 +8,7 @@ from assethelpers import getAssetRelativePath
|
|||||||
|
|
||||||
CHUNK_WIDTH = 16
|
CHUNK_WIDTH = 16
|
||||||
CHUNK_HEIGHT = 16
|
CHUNK_HEIGHT = 16
|
||||||
CHUNK_DEPTH = 8
|
CHUNK_DEPTH = 4
|
||||||
CHUNK_TILE_COUNT = CHUNK_WIDTH * CHUNK_HEIGHT * CHUNK_DEPTH
|
CHUNK_TILE_COUNT = CHUNK_WIDTH * CHUNK_HEIGHT * CHUNK_DEPTH
|
||||||
TILE_WIDTH = 16.0
|
TILE_WIDTH = 16.0
|
||||||
TILE_HEIGHT = 16.0
|
TILE_HEIGHT = 16.0
|
||||||
@@ -17,6 +17,7 @@ TILE_DEPTH = 11.36
|
|||||||
def processTile(tileIndex, x=0, y=0, z=0):
|
def processTile(tileIndex, x=0, y=0, z=0):
|
||||||
vertices = []
|
vertices = []
|
||||||
indices = []
|
indices = []
|
||||||
|
tileType = tileIndex
|
||||||
|
|
||||||
# Placement X, Y, Z
|
# Placement X, Y, Z
|
||||||
px = x * TILE_WIDTH
|
px = x * TILE_WIDTH
|
||||||
@@ -59,7 +60,8 @@ def processTile(tileIndex, x=0, y=0, z=0):
|
|||||||
|
|
||||||
return {
|
return {
|
||||||
'vertices': vertices,
|
'vertices': vertices,
|
||||||
'indices': indices
|
'indices': indices,
|
||||||
|
'tileType': tileType
|
||||||
}
|
}
|
||||||
|
|
||||||
def processChunk(path):
|
def processChunk(path):
|
||||||
@@ -88,7 +90,6 @@ def processChunk(path):
|
|||||||
|
|
||||||
for i, tile in enumerate(inData['tiles']):
|
for i, tile in enumerate(inData['tiles']):
|
||||||
# Set to chunk
|
# Set to chunk
|
||||||
chunk['tiles'][i] = tile
|
|
||||||
|
|
||||||
# Calculate x, y, z from i
|
# Calculate x, y, z from i
|
||||||
x = i % CHUNK_WIDTH
|
x = i % CHUNK_WIDTH
|
||||||
@@ -104,6 +105,7 @@ def processChunk(path):
|
|||||||
baseModel['indices'].extend(quad_indices)
|
baseModel['indices'].extend(quad_indices)
|
||||||
baseModel['vertexCount'] = len(baseModel['vertices'])
|
baseModel['vertexCount'] = len(baseModel['vertices'])
|
||||||
baseModel['indexCount'] = len(baseModel['indices'])
|
baseModel['indexCount'] = len(baseModel['indices'])
|
||||||
|
chunk['tiles'][i] = result['tileType']
|
||||||
|
|
||||||
# Generate binary buffer for efficient output
|
# Generate binary buffer for efficient output
|
||||||
buffer = bytearray()
|
buffer = bytearray()
|
||||||
|
|||||||
Reference in New Issue
Block a user