PoP roomtest: подъём/спуск на ОТКРЫТЫХ воротах (потерянная проверка openness)
Kid не мог залезть на тайл поднятой решётки: срывался обратно. can_climb_up (seg005:09DF) выбирает seq_73 («влез под решётку и съехал») только для ЗАКРЫТЫХ ворот — условие включает curr_room_modif[curr_tilepos] >> 2 < 6, а у нас его не было, и seq_73 играл при любой решётке над головой при взгляде влево. Та же дыра нашлась в спуске: down_pressed (seg005:482) запрещает climb-down с тайла ворот лицом влево тоже ТОЛЬКО пока они закрыты (|| curr_room_modif[curr_tilepos] >> 2 >= 6). Без этого Kid приседал вместо спуска даже под поднятой решёткой. Openness обеих проверок берётся общим хелпером gate_modif(col,row) (вынесен из gate_passable — умеет свою комнату и соседнюю через шов). Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
@@ -204,14 +204,21 @@ static uint8_t get_tile(int8_t col, int8_t row)
|
||||
* g_link_r col0; ВНУТРИ комнаты (0..9) — текущая комната g_room (иначе после
|
||||
* перехода Kid встаёт на ту же створку уже как на внутрикомнатную и его отбивает
|
||||
* обратно). Открыто ⇔ (modif>>2)+6 >= char_height (бары выше головы). */
|
||||
/* Живой модификатор (openness) ворот в (col,row): своя комната или соседняя
|
||||
* через шов. 0xFF — тайла нет (за краем уровня). */
|
||||
static uint8_t gate_modif(int8_t col, int8_t row)
|
||||
{
|
||||
if (row < 0 || row > 2) return 0xFF;
|
||||
if (col == -1 && g_link_l) return pop_trob_modif(g_link_l)[row * 10 + 9];
|
||||
if (col == 10 && g_link_r) return pop_trob_modif(g_link_r)[row * 10 + 0];
|
||||
if (col >= 0 && col <= 9) return pop_trob_modif(g_room)[row * 10 + col];
|
||||
return 0xFF;
|
||||
}
|
||||
|
||||
static uint8_t gate_passable(int8_t col, int8_t row)
|
||||
{
|
||||
uint8_t gm;
|
||||
if (row < 0 || row > 2) return 0;
|
||||
if (col == -1 && g_link_l) gm = pop_trob_modif(g_link_l)[row * 10 + 9];
|
||||
else if (col == 10 && g_link_r) gm = pop_trob_modif(g_link_r)[row * 10 + 0];
|
||||
else if (col >= 0 && col <= 9) gm = pop_trob_modif(g_room)[row * 10 + col];
|
||||
else return 0;
|
||||
uint8_t gm = gate_modif(col, row);
|
||||
if (gm == 0xFF) return 0;
|
||||
return (uint8_t)((gm >> 2) + 6) >= (uint8_t)kid_fp_height();
|
||||
}
|
||||
|
||||
@@ -656,13 +663,18 @@ int pop_wall_ahead(void)
|
||||
/* grab_timer истёк — можно подтягиваться? */
|
||||
uint8_t pop_hang_grab_ready(void) { return grab_timer == 0; }
|
||||
|
||||
/* can_climb_up: тайл над персонажем — обычный подъём (seq_10) либо подъём
|
||||
* к закрытой калитке/зеркалу/чомперу (seq_73). */
|
||||
/* can_climb_up (seg005:09DF): тайл над персонажем — обычный подъём (seq_10)
|
||||
* либо подъём к ЗАКРЫТОЙ калитке/зеркалу/чомперу (seq_73 = «влез и съехал
|
||||
* обратно»). Для ворот условие включает ОТКРЫТОСТЬ:
|
||||
* curr_tile2 == tiles_4_gate && direction != right && modif >> 2 < 6
|
||||
* — под поднятой решёткой (modif >> 2 >= 6) подъём обычный. Без проверки
|
||||
* модификатора Kid срывался и с открытых ворот. */
|
||||
uint8_t pop_hang_climb_up_seq(void)
|
||||
{
|
||||
uint8_t t = get_tile_above_char();
|
||||
if (((t == TILE_MIRROR || t == TILE_CHOMPER) && Kid.direction == 0) ||
|
||||
(t == TILE_GATE && Kid.direction != 0))
|
||||
(t == TILE_GATE && Kid.direction != 0 &&
|
||||
(uint8_t)(gate_modif(Kid.curr_col, (int8_t)(Kid.curr_row - 1)) >> 2) < 6))
|
||||
return SEQ_73_CLIMB_UP_TO_GATE;
|
||||
return SEQ_10_CLIMB_UP;
|
||||
}
|
||||
@@ -711,8 +723,11 @@ uint8_t pop_down_action(void)
|
||||
if (!tile_is_floor(get_tile_behind_char()) && distance_to_edge_weight() >= 8) {
|
||||
uint8_t through = get_tile_behind_char();
|
||||
get_tile_at_char(); /* g_curr_tile = под персонажем */
|
||||
/* seg005:482: спуск с тайла-ворот лицом ВЛЕВО запрещён только пока они
|
||||
* ЗАКРЫТЫ (modif >> 2 < 6); под поднятой решёткой спуск обычный. */
|
||||
if (can_grab(through) &&
|
||||
(Kid.direction >= 0 || get_tile_at_char() != TILE_GATE)) {
|
||||
(Kid.direction >= 0 || get_tile_at_char() != TILE_GATE ||
|
||||
(uint8_t)(gate_modif(Kid.curr_col, Kid.curr_row) >> 2) >= 6)) {
|
||||
Kid.x = (uint8_t)char_dx_forward((int8_t)(distance_to_edge_weight() - 9));
|
||||
kid_set_seq(SEQ_68_CLIMB_DOWN);
|
||||
return 1;
|
||||
|
||||
Reference in New Issue
Block a user