MultiplayerManager.java 5.02 KB
Newer Older
Melledy's avatar
Melledy committed
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
package emu.grasscutter.game.managers;

import emu.grasscutter.game.CoopRequest;
import emu.grasscutter.game.GenshinPlayer;
import emu.grasscutter.game.GenshinPlayer.SceneLoadState;
import emu.grasscutter.game.props.EnterReason;
import emu.grasscutter.net.proto.EnterTypeOuterClass.EnterType;
import emu.grasscutter.net.proto.PlayerApplyEnterMpReasonOuterClass.PlayerApplyEnterMpReason;
import emu.grasscutter.game.World;
import emu.grasscutter.server.game.GameServer;
import emu.grasscutter.server.packet.send.PacketPlayerApplyEnterMpNotify;
import emu.grasscutter.server.packet.send.PacketPlayerApplyEnterMpResultNotify;
import emu.grasscutter.server.packet.send.PacketPlayerEnterSceneNotify;

public class MultiplayerManager {
	private final GameServer server;
	
	public MultiplayerManager(GameServer server) {
		this.server = server;
	}

	public GameServer getServer() {
		return server;
	}

	public void applyEnterMp(GenshinPlayer player, int targetUid) {
27
		GenshinPlayer target = getServer().getPlayerByUid(targetUid);
Melledy's avatar
Melledy committed
28
29
30
31
32
33
34
35
36
37
		if (target == null) {
			player.sendPacket(new PacketPlayerApplyEnterMpResultNotify(targetUid, "", false, PlayerApplyEnterMpReason.PlayerCannotEnterMp));
			return;
		}
		
		// Sanity checks - Dont let player join if already in multiplayer
		if (player.getWorld().isMultiplayer()) {
			return;
		}
		
38
		/*
Melledy's avatar
Melledy committed
39
40
41
42
		if (target.getWorld().isDungeon()) {
			player.sendPacket(new PacketPlayerApplyEnterMpResultNotify(targetUid, "", false, PlayerApplyEnterMpReason.SceneCannotEnter));
			return;
		}
43
		*/
Melledy's avatar
Melledy committed
44
45
		
		// Get request
46
		CoopRequest request = target.getCoopRequests().get(player.getUid());
Melledy's avatar
Melledy committed
47
48
49
50
51
52
53
54
		
		if (request != null && !request.isExpired()) {
			// Join request already exists
			return;
		}
		
		// Put request in
		request = new CoopRequest(player);
55
		target.getCoopRequests().put(player.getUid(), request);
Melledy's avatar
Melledy committed
56
57
58
59
60
		
		// Packet
		target.sendPacket(new PacketPlayerApplyEnterMpNotify(player));
	}

61
	public void applyEnterMpReply(GenshinPlayer hostPlayer, int applyUid, boolean isAgreed) {
Melledy's avatar
Melledy committed
62
		// Checks
63
		CoopRequest request = hostPlayer.getCoopRequests().get(applyUid);
Melledy's avatar
Melledy committed
64
65
66
67
68
69
		if (request == null || request.isExpired()) {
			return;
		}
		
		// Remove now that we are handling it
		GenshinPlayer requester = request.getRequester();
70
		hostPlayer.getCoopRequests().remove(applyUid);
Melledy's avatar
Melledy committed
71
		
72
		// Sanity checks - Dont let the requesting player join if they are already in multiplayer
Melledy's avatar
Melledy committed
73
		if (requester.getWorld().isMultiplayer()) {
74
			request.getRequester().sendPacket(new PacketPlayerApplyEnterMpResultNotify(hostPlayer, false, PlayerApplyEnterMpReason.PlayerCannotEnterMp));
Melledy's avatar
Melledy committed
75
76
77
78
			return;
		}
		
		// Response packet
79
		request.getRequester().sendPacket(new PacketPlayerApplyEnterMpResultNotify(hostPlayer, isAgreed, PlayerApplyEnterMpReason.PlayerJudge));
Melledy's avatar
Melledy committed
80
81
82
83
84
85
86
		
		// Declined
		if (!isAgreed) {
			return;
		}

		// Success
87
		if (!hostPlayer.getWorld().isMultiplayer()) {
Melledy's avatar
Melledy committed
88
			// Player not in multiplayer, create multiplayer world
89
			World world = new World(hostPlayer, true);
Melledy's avatar
Melledy committed
90
91

			// Add
92
			world.addPlayer(hostPlayer);
Melledy's avatar
Melledy committed
93
94
			
			// Rejoin packet
95
			hostPlayer.sendPacket(new PacketPlayerEnterSceneNotify(hostPlayer, hostPlayer, EnterType.EnterSelf, EnterReason.HostFromSingleToMp, hostPlayer.getScene().getId(), hostPlayer.getPos()));
Melledy's avatar
Melledy committed
96
97
		}
		
98
99
100
101
		// Set scene pos and id of requester to the host player's
		requester.getPos().set(hostPlayer.getPos());
		requester.getRotation().set(hostPlayer.getRotation());
		requester.setSceneId(hostPlayer.getSceneId());
Melledy's avatar
Melledy committed
102
		
103
104
105
		// Make requester join
		hostPlayer.getWorld().addPlayer(requester);

Melledy's avatar
Melledy committed
106
		// Packet
107
		requester.sendPacket(new PacketPlayerEnterSceneNotify(requester, hostPlayer, EnterType.EnterOther, EnterReason.TeamJoin, hostPlayer.getScene().getId(), hostPlayer.getPos()));
Melledy's avatar
Melledy committed
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
	}
	
	public boolean leaveCoop(GenshinPlayer player) {
		// Make sure player's world is multiplayer
		if (!player.getWorld().isMultiplayer()) {
			return false;
		}
		
		// Make sure everyone's scene is loaded
		for (GenshinPlayer p : player.getWorld().getPlayers()) {
			if (p.getSceneLoadState() != SceneLoadState.LOADED) {
				return false;
			}
		}
		
		// Create new world for player
		World world = new World(player);
		world.addPlayer(player);
	
		// Packet
128
		player.sendPacket(new PacketPlayerEnterSceneNotify(player, EnterType.EnterSelf, EnterReason.TeamBack, player.getScene().getId(), player.getPos()));
Melledy's avatar
Melledy committed
129
130
131
132
133
134
135
136
137
138
139
		
		return true;
	}

	public boolean kickPlayer(GenshinPlayer player, int targetUid) {
		// Make sure player's world is multiplayer and that player is owner
		if (!player.getWorld().isMultiplayer() || player.getWorld().getHost() != player) {
			return false;
		}
		
		// Get victim and sanity checks
140
		GenshinPlayer victim = player.getServer().getPlayerByUid(targetUid);
Melledy's avatar
Melledy committed
141
142
143
144
145
146
147
148
149
150
151
152
153
154
		
		if (victim == null || victim == player) {
			return false;
		}
		
		// Make sure victim's scene has loaded
		if (victim.getSceneLoadState() != SceneLoadState.LOADED) {
			return false;
		}
		
		// Kick
		World world = new World(victim);
		world.addPlayer(victim);
		
155
		victim.sendPacket(new PacketPlayerEnterSceneNotify(victim, EnterType.EnterSelf, EnterReason.TeamKick, victim.getScene().getId(), victim.getPos()));
Melledy's avatar
Melledy committed
156
157
158
		return true;
	}
}