Кусок узора на стене: модификатор стены не переводился при загрузке
Флаг «no blue» лежит в нулевом бите модификатора стены В ФАЙЛЕ уровня, а отрисовка (как и оригинал) ищет его в СТАРШЕМ: load_alter_mod переводит их сдвигом на 7. Ветку стен мы пропускали намеренно — связи кладки считаются по соседям, — но noblue из соседей не выводится. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
@@ -2864,3 +2864,48 @@ seg006:507). Выход из функции теперь один на обе
|
||||
класс целиком, а не найденный путь. Ловушка на будущее, если симптом
|
||||
всплывёт снова: `wp <адрес pop_cd[OPP].w>,4,w` — сработает на первой же
|
||||
записи «чужой» ширины.
|
||||
|
||||
---
|
||||
|
||||
<a id="blueline-noblue"></a>
|
||||
## BLUELINE-NOBLUE. Кусок синего узора на стене там, где оригинал его не рисует — ЗАКРЫТ 2026-08-18
|
||||
|
||||
**Наблюдение (пользователь, 2026-08-18).** Уровень 6, комната 1, тайл (2,3):
|
||||
у правой кромки левого блока висит небольшой кусочек тёмно-синего узора,
|
||||
которого в оригинале нет. Диагноз пользователя («первоначальная отрисовка
|
||||
фона, фикс не должен повлиять на скорость») подтвердился полностью.
|
||||
|
||||
**Корень.** Полоску рисует `draw_tile_right` (`pop_room.c`, порт
|
||||
seg008:0666) — её кладёт ПРАВЫЙ сосед стены:
|
||||
|
||||
```c
|
||||
case tiles_20_wall:
|
||||
if (tbl_level_type[current_level] && (modifier_left & 0x80) == 0)
|
||||
add_backtable(chtab_6, 84 /*wall stripe*/, draw_xh + 3, 0, draw_main_y - 27, ...);
|
||||
```
|
||||
|
||||
Проверка `& 0x80` у нас была, а вот значения, которое она проверяет, — нет.
|
||||
Модификатор стены В ФАЙЛЕ уровня и В РАНТАЙМЕ у оригинала разные:
|
||||
`load_alter_mod` (seg008:1216) переводит их при загрузке комнаты —
|
||||
`*curr_tile_modif <<= 7`, то есть единственный бит уровня («no blue»,
|
||||
авторский флаг «не рисовать полоску на моей правой кромке») переезжает в
|
||||
СТАРШИЙ. Наш порт `load_alter_mod` (`pop_trob.c`) ветку стен пропускал
|
||||
НАМЕРЕННО, и в комментарии это было записано: связи кладки мы считаем по
|
||||
типам соседей (`pop_wall_modifier`), сохранённый модификатор стены «не
|
||||
читается вовсе».
|
||||
|
||||
Ошибка в слове «вовсе»: у модификатора стены ДВА независимых смысла, и
|
||||
из соседей выводится только один. `noblue` проставлен вручную в данных
|
||||
уровня и не выводится ниоткуда. В комнате 1 уровня 6 стена (2,2) имеет в
|
||||
файле модификатор 1, то есть ровно «без полоски»; без перевода отрисовка
|
||||
видела сырую единицу, `(1 & 0x80) == 0` проходило — и полоска вылезала.
|
||||
|
||||
**Фикс.** `case TILE_WALL: *m = (uint8_t)(*m << 7);` в порте
|
||||
`load_alter_mod`. Перевод одноразовый, при первом входе в комнату
|
||||
(`room_seen`), — кадровый бюджет не трогает вообще; +24 байта в банке 6,
|
||||
резидент не изменился.
|
||||
|
||||
**Проверка (MAME, уровень 6 комната 1).** Попиксельный диф скриншотов до и
|
||||
после: изменения ровно в боксе `(344,199)-(358,206)`, 38 пикселей — сам
|
||||
артефакт и ничего кроме. На подземных уровнях изменений нет по построению:
|
||||
полоска целиком под `if (PALACE)`.
|
||||
|
||||
@@ -30,6 +30,7 @@
|
||||
#define TILE_SWORD 0x16 /* меч-предмет на полу */
|
||||
#define TILE_LEVELDOOR 0x10 /* левая половина двери уровня (на ней modif) */
|
||||
#define TILE_CHOMP 0x12 /* чомпер (челюсти) */
|
||||
#define TILE_WALL 0x14 /* стена (в модификаторе — флаг «без полоски») */
|
||||
#define TILE_TORCH 0x13
|
||||
#define TILE_TORCH_DEBRIS 0x1E
|
||||
#define TILE_EMPTY 0x00 /* remove_loose: на месте провалившейся плиты */
|
||||
@@ -91,10 +92,17 @@ uint8_t *pop_trob_modif(uint8_t room) __banked
|
||||
* рядом с ними теряет смысл (ур. 2, комн. 13).
|
||||
* loose -> 0: фаза тряски всегда начинается с нуля.
|
||||
* зелье -> <<3: старшие биты = тип, младшие 3 = фаза пузырька.
|
||||
* стена -> <<7: единственный бит уровня («без полоски», см. ниже)
|
||||
* переезжает в СТАРШИЙ, где его и ищет отрисовка.
|
||||
*
|
||||
* Ветка стен (blue-line/связи кладки) НЕ портируется намеренно: у
|
||||
* нас pop_bg считает связи по типам СОСЕДЕЙ прямо при отрисовке
|
||||
* (wall_modifier), сохранённый модификатор стены не читается вовсе. */
|
||||
* СВЯЗИ кладки (какая грань у стены слева/справа) из этого перевода
|
||||
* намеренно выкинуты: у нас их считает pop_wall_modifier по типам
|
||||
* СОСЕДЕЙ прямо при отрисовке. Но второй смысл модификатора стены —
|
||||
* авторский флаг «не рисовать синюю полоску на моей правой кромке»
|
||||
* (noblue) — из соседей не выводится, он проставлен вручную в данных
|
||||
* уровня. Без перевода отрисовка видела сырую единицу вместо 0x80,
|
||||
* проверка `(mod & 0x80) == 0` проходила, и во дворце вылезал кусок
|
||||
* узора на стене (BUG BLUELINE-NOBLUE, ур. 6 к. 1 тайл (2,3)). */
|
||||
pop_level_access_begin();
|
||||
for (i = 0; i < POP_ROOMTILES; i++) {
|
||||
uint8_t *m = &room_modif[room - 1][i];
|
||||
@@ -102,6 +110,7 @@ uint8_t *pop_trob_modif(uint8_t room) __banked
|
||||
case TILE_GATE: *m = (uint8_t)((*m == 1) ? 188 : 0); break;
|
||||
case TILE_LOOSE: *m = 0; break;
|
||||
case TILE_POTION: *m = (uint8_t)(*m << 3); break;
|
||||
case TILE_WALL: *m = (uint8_t)(*m << 7); break;
|
||||
default: break;
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user