Allow yellow tanks into fire and rovers into more tiles

This commit is contained in:
Eevee (Evelyn Woods) 2021-05-03 21:38:42 -06:00
parent 7c498f195e
commit 49b691adde
2 changed files with 35 additions and 33 deletions

View File

@ -92,12 +92,12 @@ export const COLLISION = {
monster_generic: 0x0100, monster_generic: 0x0100,
fireball: 0x0200, fireball: 0x0200,
bug: 0x0400, bug: 0x0400,
yellow_tank: 0x0800,
rover: 0x1000, rover: 0x1000,
ghost: 0x8000, ghost: 0x8000,
// For a tile's COLLISION, use one of these bit combinations // For a tile's COLLISION, use one of these bit combinations
monster_general: 0x6f00, // everything but ghost and rover monster_typical: 0x6f00, // everything but ghost and rover
monster_solid: 0x7f00, // everything but ghost monster_any: 0xff00, // everything including ghost (only used for monster/fire compat flag)
monster_any: 0xff00, // everything including ghost
// Combo masks used for matching // Combo masks used for matching
all_but_ghost: 0xffff & ~0x8000, all_but_ghost: 0xffff & ~0x8000,
@ -110,6 +110,8 @@ export const COLLISION = {
export const PICKUP_PRIORITIES = { export const PICKUP_PRIORITIES = {
never: 4, // cc2 blocks, never pick anything up never: 4, // cc2 blocks, never pick anything up
always: 3, // all actors; blue keys, yellow teleporters (everything picks up except cc2 blocks) always: 3, // all actors; blue keys, yellow teleporters (everything picks up except cc2 blocks)
// TODO is this even necessary? in cc2 the general rule seems to be that anything stepping on
// an item picks it up, and collision is used to avoid that most of the time
normal: 2, // actors with inventories; most items normal: 2, // actors with inventories; most items
player: 1, // players and doppelgangers; red keys (ignored by everything else) player: 1, // players and doppelgangers; red keys (ignored by everything else)
real_player: 0, real_player: 0,

View File

@ -52,7 +52,7 @@ function _define_door(key) {
return { return {
layer: LAYERS.terrain, layer: LAYERS.terrain,
// Doors can be opened by ice blocks, but not dirt blocks or monsters // Doors can be opened by ice blocks, but not dirt blocks or monsters
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_general, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
blocks(me, level, other) { blocks(me, level, other) {
if (other.type.name === 'ghost') if (other.type.name === 'ghost')
return false; return false;
@ -73,7 +73,7 @@ function _define_gate(key) {
return { return {
layer: LAYERS.item, layer: LAYERS.item,
// Doors can be opened by ice blocks, but not dirt blocks or monsters // Doors can be opened by ice blocks, but not dirt blocks or monsters
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_general, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
blocks(me, level, other) { blocks(me, level, other) {
if (other.type.name === 'ghost') if (other.type.name === 'ghost')
return false; return false;
@ -244,7 +244,7 @@ const COMMON_TOOL = {
layer: LAYERS.item, layer: LAYERS.item,
is_item: true, is_item: true,
is_tool: true, is_tool: true,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_general, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
item_priority: PICKUP_PRIORITIES.normal, item_priority: PICKUP_PRIORITIES.normal,
}; };
@ -343,7 +343,7 @@ const TILE_TYPES = {
}, },
popwall: { popwall: {
layer: LAYERS.terrain, layer: LAYERS.terrain,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_general, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
on_ready(me, level) { on_ready(me, level) {
if (! level.compat.no_auto_convert_ccl_popwalls && if (! level.compat.no_auto_convert_ccl_popwalls &&
level.stored_level.format === 'ccl' && level.stored_level.format === 'ccl' &&
@ -366,7 +366,7 @@ const TILE_TYPES = {
// with popwall behavior between Lynx and Steam // with popwall behavior between Lynx and Steam
popwall2: { popwall2: {
layer: LAYERS.terrain, layer: LAYERS.terrain,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_solid, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
on_depart(me, level, other) { on_depart(me, level, other) {
level.spawn_animation(me.cell, 'puff'); level.spawn_animation(me.cell, 'puff');
level.transmute_tile(me, 'popwall'); level.transmute_tile(me, 'popwall');
@ -424,7 +424,7 @@ const TILE_TYPES = {
}, },
fake_floor: { fake_floor: {
layer: LAYERS.terrain, layer: LAYERS.terrain,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_general, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
reveal(me, level, other) { reveal(me, level, other) {
level.spawn_animation(me.cell, 'puff'); level.spawn_animation(me.cell, 'puff');
level.transmute_tile(me, 'floor'); level.transmute_tile(me, 'floor');
@ -694,7 +694,7 @@ const TILE_TYPES = {
// Terrain // Terrain
dirt: { dirt: {
layer: LAYERS.terrain, layer: LAYERS.terrain,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_general, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
blocks(me, level, other) { blocks(me, level, other) {
return ((other.type.name === 'player2' || other.type.name === 'doppelganger2') && return ((other.type.name === 'player2' || other.type.name === 'doppelganger2') &&
! other.has_item('hiking_boots')); ! other.has_item('hiking_boots'));
@ -711,7 +711,7 @@ const TILE_TYPES = {
}, },
gravel: { gravel: {
layer: LAYERS.terrain, layer: LAYERS.terrain,
blocks_collision: COLLISION.monster_general, blocks_collision: COLLISION.monster_typical,
blocks(me, level, other) { blocks(me, level, other) {
return ((other.type.name === 'player2' || other.type.name === 'doppelganger2') && return ((other.type.name === 'player2' || other.type.name === 'doppelganger2') &&
! other.has_item('hiking_boots')); ! other.has_item('hiking_boots'));
@ -778,7 +778,7 @@ const TILE_TYPES = {
layer: LAYERS.terrain, layer: LAYERS.terrain,
// Fire blocks most monsters, except in MS where they walk right in and get roasted // Fire blocks most monsters, except in MS where they walk right in and get roasted
blocks(me, level, other) { blocks(me, level, other) {
if (other.type.collision_mask & (COLLISION.fireball | COLLISION.ghost)) if (other.type.collision_mask & (COLLISION.fireball | COLLISION.yellow_tank | COLLISION.ghost))
return false; return false;
if (other.type.collision_mask & COLLISION.monster_any) { if (other.type.collision_mask & COLLISION.monster_any) {
return ! level.compat.fire_allows_monsters; return ! level.compat.fire_allows_monsters;
@ -1036,7 +1036,7 @@ const TILE_TYPES = {
// TODO ms: this is random, and an acting wall to monsters (!) // TODO ms: this is random, and an acting wall to monsters (!)
blocks(me, level, other) { blocks(me, level, other) {
return (level.compat.rff_blocks_monsters && return (level.compat.rff_blocks_monsters &&
(other.type.collision_mask & COLLISION.monster_general)); (other.type.collision_mask & COLLISION.monster_typical));
}, },
on_arrive(me, level, other) { on_arrive(me, level, other) {
level.set_actor_direction(other, level.get_force_floor_direction()); level.set_actor_direction(other, level.get_force_floor_direction());
@ -1115,7 +1115,7 @@ const TILE_TYPES = {
}, },
thief_tools: { thief_tools: {
layer: LAYERS.terrain, layer: LAYERS.terrain,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_solid, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
on_arrive(me, level, other) { on_arrive(me, level, other) {
if (level.take_tool_from_actor(other, 'bribe')) { if (level.take_tool_from_actor(other, 'bribe')) {
if (other === level.player) { if (other === level.player) {
@ -1138,7 +1138,7 @@ const TILE_TYPES = {
}, },
thief_keys: { thief_keys: {
layer: LAYERS.terrain, layer: LAYERS.terrain,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_solid, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
on_arrive(me, level, other) { on_arrive(me, level, other) {
if (level.take_tool_from_actor(other, 'bribe')) { if (level.take_tool_from_actor(other, 'bribe')) {
if (other === level.player) { if (other === level.player) {
@ -1163,7 +1163,6 @@ const TILE_TYPES = {
no_sign: { no_sign: {
layer: LAYERS.item_mod, layer: LAYERS.item_mod,
item_modifier: 'ignore', item_modifier: 'ignore',
collision_allow: COLLISION.monster_solid,
blocks(me, level, other) { blocks(me, level, other) {
let item = me.cell.get_item(); let item = me.cell.get_item();
return item && other.has_item(item.type.name); return item && other.has_item(item.type.name);
@ -1357,7 +1356,7 @@ const TILE_TYPES = {
layer: LAYERS.item, layer: LAYERS.item,
is_chip: true, is_chip: true,
is_required_chip: true, is_required_chip: true,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_general, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
item_priority: PICKUP_PRIORITIES.real_player, item_priority: PICKUP_PRIORITIES.real_player,
on_pickup(me, level, other) { on_pickup(me, level, other) {
level.collect_chip(); level.collect_chip();
@ -1488,7 +1487,7 @@ const TILE_TYPES = {
// Floor mechanisms // Floor mechanisms
cloner: { cloner: {
layer: LAYERS.terrain, layer: LAYERS.terrain,
blocks_collision: COLLISION.real_player | COLLISION.block_cc1 | COLLISION.monster_solid, blocks_collision: COLLISION.real_player | COLLISION.block_cc1 | COLLISION.monster_typical,
populate_defaults(me) { populate_defaults(me) {
me.arrows = 0; // bitmask of glowing arrows (visual, no gameplay impact) me.arrows = 0; // bitmask of glowing arrows (visual, no gameplay impact)
}, },
@ -2429,7 +2428,7 @@ const TILE_TYPES = {
// Time alteration // Time alteration
stopwatch_bonus: { stopwatch_bonus: {
layer: LAYERS.item, layer: LAYERS.item,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_solid, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
item_priority: PICKUP_PRIORITIES.real_player, item_priority: PICKUP_PRIORITIES.real_player,
on_pickup(me, level, other) { on_pickup(me, level, other) {
level.sfx.play_once('get-stopwatch-bonus', me.cell); level.sfx.play_once('get-stopwatch-bonus', me.cell);
@ -2439,7 +2438,7 @@ const TILE_TYPES = {
}, },
stopwatch_penalty: { stopwatch_penalty: {
layer: LAYERS.item, layer: LAYERS.item,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_solid, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
item_priority: PICKUP_PRIORITIES.real_player, item_priority: PICKUP_PRIORITIES.real_player,
on_pickup(me, level, other) { on_pickup(me, level, other) {
level.sfx.play_once('get-stopwatch-penalty', me.cell); level.sfx.play_once('get-stopwatch-penalty', me.cell);
@ -2449,7 +2448,7 @@ const TILE_TYPES = {
}, },
stopwatch_toggle: { stopwatch_toggle: {
layer: LAYERS.item, layer: LAYERS.item,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_solid, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
item_priority: PICKUP_PRIORITIES.player, item_priority: PICKUP_PRIORITIES.player,
on_pickup(me, level, other) { on_pickup(me, level, other) {
level.sfx.play_once('get-stopwatch-toggle', me.cell); level.sfx.play_once('get-stopwatch-toggle', me.cell);
@ -2522,6 +2521,7 @@ const TILE_TYPES = {
}, },
tank_yellow: { tank_yellow: {
...COMMON_MONSTER, ...COMMON_MONSTER,
collision_mask: COLLISION.yellow_tank,
pushes: { pushes: {
dirt_block: true, dirt_block: true,
ice_block: true, ice_block: true,
@ -2704,14 +2704,14 @@ const TILE_TYPES = {
is_item: true, is_item: true,
is_key: true, is_key: true,
// FIXME ok this is ghastly // FIXME ok this is ghastly
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_general, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
item_priority: PICKUP_PRIORITIES.normal, item_priority: PICKUP_PRIORITIES.normal,
}, },
key_green: { key_green: {
layer: LAYERS.item, layer: LAYERS.item,
is_item: true, is_item: true,
is_key: true, is_key: true,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_general, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
item_priority: PICKUP_PRIORITIES.normal, item_priority: PICKUP_PRIORITIES.normal,
}, },
// Boots // Boots
@ -3081,7 +3081,7 @@ const TILE_TYPES = {
layer: LAYERS.item, layer: LAYERS.item,
is_chip: true, is_chip: true,
is_required_chip: true, is_required_chip: true,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_general, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
item_priority: PICKUP_PRIORITIES.real_player, item_priority: PICKUP_PRIORITIES.real_player,
on_pickup(me, level, other) { on_pickup(me, level, other) {
level.collect_chip(); level.collect_chip();
@ -3091,7 +3091,7 @@ const TILE_TYPES = {
chip_extra: { chip_extra: {
layer: LAYERS.item, layer: LAYERS.item,
is_chip: true, is_chip: true,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_general, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
item_priority: PICKUP_PRIORITIES.real_player, item_priority: PICKUP_PRIORITIES.real_player,
on_pickup(me, level, other) { on_pickup(me, level, other) {
level.collect_chip(); level.collect_chip();
@ -3102,7 +3102,7 @@ const TILE_TYPES = {
// actually add to the player's bonus // actually add to the player's bonus
score_10: { score_10: {
layer: LAYERS.item, layer: LAYERS.item,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_general, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
item_priority: PICKUP_PRIORITIES.normal, item_priority: PICKUP_PRIORITIES.normal,
on_pickup(me, level, other) { on_pickup(me, level, other) {
if (other.type.name === 'ghost') if (other.type.name === 'ghost')
@ -3116,7 +3116,7 @@ const TILE_TYPES = {
}, },
score_100: { score_100: {
layer: LAYERS.item, layer: LAYERS.item,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_general, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
item_priority: PICKUP_PRIORITIES.normal, item_priority: PICKUP_PRIORITIES.normal,
on_pickup(me, level, other) { on_pickup(me, level, other) {
if (other.type.name === 'ghost') if (other.type.name === 'ghost')
@ -3130,7 +3130,7 @@ const TILE_TYPES = {
}, },
score_1000: { score_1000: {
layer: LAYERS.item, layer: LAYERS.item,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_general, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
item_priority: PICKUP_PRIORITIES.normal, item_priority: PICKUP_PRIORITIES.normal,
on_pickup(me, level, other) { on_pickup(me, level, other) {
if (other.type.name === 'ghost') if (other.type.name === 'ghost')
@ -3144,7 +3144,7 @@ const TILE_TYPES = {
}, },
score_2x: { score_2x: {
layer: LAYERS.item, layer: LAYERS.item,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_general, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
item_priority: PICKUP_PRIORITIES.normal, item_priority: PICKUP_PRIORITIES.normal,
on_pickup(me, level, other) { on_pickup(me, level, other) {
if (other.type.name === 'ghost') if (other.type.name === 'ghost')
@ -3158,7 +3158,7 @@ const TILE_TYPES = {
}, },
score_5x: { score_5x: {
layer: LAYERS.item, layer: LAYERS.item,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_general, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
item_priority: PICKUP_PRIORITIES.normal, item_priority: PICKUP_PRIORITIES.normal,
on_pickup(me, level, other) { on_pickup(me, level, other) {
if (other.type.name === 'ghost') if (other.type.name === 'ghost')
@ -3174,14 +3174,14 @@ const TILE_TYPES = {
hint: { hint: {
layer: LAYERS.terrain, layer: LAYERS.terrain,
is_hint: true, is_hint: true,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_solid, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
populate_defaults(me) { populate_defaults(me) {
me.hint_text = null; // optional, may use level's hint instead me.hint_text = null; // optional, may use level's hint instead
}, },
}, },
socket: { socket: {
layer: LAYERS.terrain, layer: LAYERS.terrain,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_general, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
blocks(me, level, other) { blocks(me, level, other) {
return ! (other.type.name === 'ghost' || level.chips_remaining <= 0); return ! (other.type.name === 'ghost' || level.chips_remaining <= 0);
}, },
@ -3195,7 +3195,7 @@ const TILE_TYPES = {
}, },
exit: { exit: {
layer: LAYERS.terrain, layer: LAYERS.terrain,
blocks_collision: COLLISION.block_cc1 | COLLISION.monster_general, blocks_collision: COLLISION.block_cc1 | COLLISION.monster_typical,
on_arrive(me, level, other) { on_arrive(me, level, other) {
if (other.type.is_real_player) { if (other.type.is_real_player) {
level.remaining_players -= 1; level.remaining_players -= 1;