mirror of
https://github.com/coop-deluxe/sm64coopdx.git
synced 2025-01-23 16:14:47 -05:00
Synchronized teleports (e.g. flowerbed) and star collection
Fixed infinite packet_level_warp sending
This commit is contained in:
parent
6bc4bfea62
commit
e0b86b7d59
8 changed files with 79 additions and 14 deletions
|
@ -812,10 +812,17 @@ u32 interact_star_or_key(struct MarioState *m, UNUSED u32 interactType, struct O
|
|||
m->usedObj = o;
|
||||
|
||||
starIndex = (o->oBehParams >> 24) & 0x1F;
|
||||
|
||||
if (m == &gMarioStates[0]) {
|
||||
// sync the star collection
|
||||
network_send_collect_star(m->numCoins, starIndex);
|
||||
}
|
||||
save_file_collect_star_or_key(m->numCoins, starIndex);
|
||||
|
||||
m->numStars =
|
||||
save_file_get_total_star_count(gCurrSaveFileNum - 1, COURSE_MIN - 1, COURSE_MAX - 1);
|
||||
s32 numStars = save_file_get_total_star_count(gCurrSaveFileNum - 1, COURSE_MIN - 1, COURSE_MAX - 1);
|
||||
for (int i = 0; i < 2; i++) {
|
||||
gMarioStates[i].numStars = numStars;
|
||||
}
|
||||
|
||||
if (!noExit) {
|
||||
drop_queued_background_music();
|
||||
|
@ -859,6 +866,11 @@ u32 interact_bbh_entrance(struct MarioState *m, UNUSED u32 interactType, struct
|
|||
u32 interact_warp(struct MarioState *m, UNUSED u32 interactType, struct Object *o) {
|
||||
u32 action;
|
||||
|
||||
if (m != &gMarioStates[0]) {
|
||||
// don't do for remote players
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (o->oInteractionSubtype & INT_SUBTYPE_FADING_WARP) {
|
||||
action = m->action;
|
||||
|
||||
|
@ -1792,7 +1804,10 @@ void mario_process_interactions(struct MarioState *m) {
|
|||
sDisplayingDoorText = FALSE;
|
||||
}
|
||||
if (!(m->marioObj->collidedObjInteractTypes & INTERACT_WARP)) {
|
||||
sJustTeleported = FALSE;
|
||||
if (m == &gMarioStates[0]) {
|
||||
// limit to only local mario
|
||||
sJustTeleported = FALSE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -884,9 +884,8 @@ void initiate_delayed_warp(void) {
|
|||
|
||||
default:
|
||||
warpNode = area_get_warp_node(sSourceWarpNodeId);
|
||||
|
||||
initiate_warp(warpNode->node.destLevel & 0x7F, warpNode->node.destArea,
|
||||
warpNode->node.destNode, sDelayedWarpArg);
|
||||
warpNode->node.destNode, sDelayedWarpArg);
|
||||
|
||||
check_if_should_set_warp_checkpoint(&warpNode->node);
|
||||
if (sWarpDest.type != WARP_TYPE_CHANGE_LEVEL) {
|
||||
|
|
|
@ -1436,7 +1436,10 @@ s32 act_teleport_fade_out(struct MarioState *m) {
|
|||
}
|
||||
|
||||
if (m->actionTimer++ == 20) {
|
||||
level_trigger_warp(m, WARP_OP_TELEPORT);
|
||||
if (m == &gMarioStates[0]) {
|
||||
// only do for local player
|
||||
level_trigger_warp(m, WARP_OP_TELEPORT);
|
||||
}
|
||||
}
|
||||
|
||||
stop_and_set_height_to_floor(m);
|
||||
|
|
|
@ -474,6 +474,7 @@ void save_file_reload(void) {
|
|||
* If coin score is greater than the current high score, update it.
|
||||
*/
|
||||
void save_file_collect_star_or_key(s16 coinScore, s16 starIndex) {
|
||||
|
||||
s32 fileIndex = gCurrSaveFileNum - 1;
|
||||
s32 courseIndex = gCurrCourseNum - 1;
|
||||
|
||||
|
|
|
@ -110,6 +110,7 @@ void network_update(void) {
|
|||
case PACKET_OBJECT: network_receive_object(&p); break;
|
||||
case PACKET_LEVEL_WARP: network_receive_level_warp(&p); break;
|
||||
case PACKET_INSIDE_PAINTING: network_receive_inside_painting(&p); break;
|
||||
case PACKET_COLLECT_STAR: network_receive_collect_star(&p); break;
|
||||
default: printf("%s received unknown packet: %d\n", NETWORKTYPESTR, p.buffer[0]);
|
||||
}
|
||||
|
||||
|
|
|
@ -20,6 +20,7 @@ enum PacketType {
|
|||
PACKET_OBJECT,
|
||||
PACKET_LEVEL_WARP,
|
||||
PACKET_INSIDE_PAINTING,
|
||||
PACKET_COLLECT_STAR,
|
||||
};
|
||||
|
||||
struct Packet {
|
||||
|
@ -78,4 +79,6 @@ void network_receive_level_warp(struct Packet* p);
|
|||
void network_update_inside_painting(void);
|
||||
void network_receive_inside_painting(struct Packet* p);
|
||||
|
||||
void network_send_collect_star(s16 coinScore, s16 starIndex);
|
||||
void network_receive_collect_star(struct Packet* p);
|
||||
#endif
|
||||
|
|
39
src/pc/network/packets/packet_collect_star.c
Normal file
39
src/pc/network/packets/packet_collect_star.c
Normal file
|
@ -0,0 +1,39 @@
|
|||
#include <stdio.h>
|
||||
#include "../network.h"
|
||||
#include "course_table.h"
|
||||
|
||||
extern s16 gCurrSaveFileNum;
|
||||
extern s16 gCurrCourseNum;
|
||||
|
||||
void network_send_collect_star(s16 coinScore, s16 starIndex) {
|
||||
struct Packet p;
|
||||
packet_init(&p, PACKET_COLLECT_STAR, true);
|
||||
|
||||
packet_write(&p, &gCurrSaveFileNum, sizeof(s16));
|
||||
packet_write(&p, &gCurrCourseNum, sizeof(s16));
|
||||
packet_write(&p, &coinScore, sizeof(s16));
|
||||
packet_write(&p, &starIndex, sizeof(s16));
|
||||
|
||||
network_send(&p);
|
||||
}
|
||||
|
||||
void network_receive_collect_star(struct Packet* p) {
|
||||
s16 coinScore, starIndex;
|
||||
s16 lastSaveFileNum = gCurrSaveFileNum;
|
||||
s16 lastCourseNum = gCurrCourseNum;
|
||||
|
||||
packet_read(p, &gCurrSaveFileNum, sizeof(s16));
|
||||
packet_read(p, &gCurrCourseNum, sizeof(s16));
|
||||
packet_read(p, &coinScore, sizeof(s16));
|
||||
packet_read(p, &starIndex, sizeof(s16));
|
||||
|
||||
save_file_collect_star_or_key(coinScore, starIndex);
|
||||
|
||||
s32 numStars = save_file_get_total_star_count(gCurrSaveFileNum - 1, COURSE_MIN - 1, COURSE_MAX - 1);
|
||||
for (int i = 0; i < 2; i++) {
|
||||
gMarioStates[i].numStars = numStars;
|
||||
}
|
||||
|
||||
gCurrSaveFileNum = lastSaveFileNum;
|
||||
gCurrCourseNum = lastCourseNum;
|
||||
}
|
|
@ -3,7 +3,7 @@
|
|||
#include "src/game/level_update.h"
|
||||
#include "src/game/area.h"
|
||||
|
||||
int warpTimeout = 0;
|
||||
int matchCount = 0;
|
||||
|
||||
void network_send_level_warp(void) {
|
||||
struct Packet p;
|
||||
|
@ -17,7 +17,6 @@ void network_send_level_warp(void) {
|
|||
}
|
||||
|
||||
void network_receive_level_warp(struct Packet* p) {
|
||||
if (warpTimeout != 0) { return; }
|
||||
s16 remotePlayMode;
|
||||
s16 remoteLevelNum;
|
||||
s32 remoteWarpArg;
|
||||
|
@ -28,16 +27,25 @@ void network_receive_level_warp(struct Packet* p) {
|
|||
packet_read(p, &remoteWarpArg, 4);
|
||||
packet_read(p, &remoteWarpNodeId, 2);
|
||||
|
||||
if (gCurrLevelNum == remoteLevelNum) {
|
||||
bool matching = (remoteLevelNum == gCurrLevelNum)
|
||||
&& (remoteWarpArg == sDelayedWarpArg)
|
||||
&& (remoteWarpNodeId == sSourceWarpNodeId);
|
||||
|
||||
if (matching) {
|
||||
if (sCurrPlayMode == PLAY_MODE_SYNC_LEVEL) {
|
||||
// our levels match now, lets play!
|
||||
set_play_mode(PLAY_MODE_NORMAL);
|
||||
set_menu_mode((s16)-1);
|
||||
}
|
||||
// our levels match, make sure the other player knows that
|
||||
network_send_level_warp();
|
||||
if (matchCount++ < 3) {
|
||||
network_send_level_warp();
|
||||
} else {
|
||||
matchCount = 0;
|
||||
}
|
||||
return;
|
||||
}
|
||||
matchCount = 0;
|
||||
|
||||
// remote isn't trying to sync, don't warp
|
||||
if (remotePlayMode != PLAY_MODE_SYNC_LEVEL) { return; }
|
||||
|
@ -50,12 +58,8 @@ void network_receive_level_warp(struct Packet* p) {
|
|||
sDelayedWarpArg = remoteWarpArg;
|
||||
sSourceWarpNodeId = remoteWarpNodeId;
|
||||
sDelayedWarpOp = WARP_OP_FORCE_SYNC;
|
||||
|
||||
// don't repeat the warp too quickly
|
||||
warpTimeout = 2;
|
||||
}
|
||||
|
||||
void network_update_level_warp(void) {
|
||||
network_send_level_warp();
|
||||
if (warpTimeout > 0) { warpTimeout--; }
|
||||
}
|
Loading…
Add table
Reference in a new issue