Skip to content

Commit

Permalink
Prismarine: Fix incorrect spawn location.
Browse files Browse the repository at this point in the history
  • Loading branch information
filiphsps committed Apr 16, 2024
1 parent 53b256d commit 07bc6d0
Show file tree
Hide file tree
Showing 18 changed files with 140 additions and 174 deletions.
5 changes: 5 additions & 0 deletions .changeset/healthy-knives-tap.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"@jsprismarine/prismarine": patch
---

Move `pitch`, `yaw` and `headYaw` to `Entity`.
7 changes: 7 additions & 0 deletions .changeset/six-pumpkins-obey.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
---
"@jsprismarine/prismarine": patch
---

Fix spawn location.
Send entity metadata to clients.
Slightly Simplify working with positions.
1 change: 1 addition & 0 deletions .vscode/settings.json
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,7 @@
"Shulker",
"SUBCHUNK",
"SUBCHUNKS",
"Varint",
"Zoglin"
],
"typescript.preferences.importModuleSpecifier": "non-relative",
Expand Down
1 change: 0 additions & 1 deletion packages/logger/src/logger.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@ import { PrismarineTransport } from './transport';
export type LogLevel = 'error' | 'warn' | 'info' | 'verbose' | 'debug' | 'silly';

export class Logger {
public static logFile: string;
private logger!: Winston;

public constructor(level: LogLevel = 'info', transports: TransportStream[] = []) {
Expand Down
49 changes: 21 additions & 28 deletions packages/prismarine/src/Player.ts
Original file line number Diff line number Diff line change
Expand Up @@ -59,10 +59,6 @@ export default class Player extends Human {
public viewDistance = 0;
public gamemode = 0;

public pitch = 0;
public yaw = 0;
public headYaw = 0;

private onGround = false;
private sprinting = false;
private flying = false;
Expand Down Expand Up @@ -109,21 +105,19 @@ export default class Player extends Human {
}

public async enable() {
this.permissions = await this.server.getPermissionManager().getPermissions(this);
const playerData = await this.getWorld().getPlayerData(this);

if (playerData.position) {
this.setPosition({
position: new Vector3(
playerData.position.x || 0,
playerData.position.y || 0,
playerData.position.z || 0
),
pitch: playerData.position.pitch || 0,
yaw: playerData.position.yaw || 0,
type: MovementType.Reset
});
}
this.permissions = await this.server.getPermissionManager().getPermissions(this);

this.setPosition({
position: playerData.position
? Vector3.fromObject(playerData.position)
: await this.getWorld().getSpawnPosition(),
pitch: playerData.position?.pitch || 0,
yaw: playerData.position?.yaw || 0,
headYaw: playerData.position?.headYaw || 0,
type: MovementType.Reset
});

this.gamemode = Gamemode.getGamemodeId(playerData.gamemode || this.server.getConfig().getGamemode());

Expand Down Expand Up @@ -326,8 +320,6 @@ export default class Player extends Human {
* Player spawning logic.
*/
public async sendSpawn() {
await this.enable();

await this.sendPosition();
await this.setGamemode(this.gamemode);
await this.getNetworkSession().sendInventory();
Expand Down Expand Up @@ -407,9 +399,7 @@ export default class Player extends Human {
}

public getXUID(): string {
if (!this.xuid) throw new Error('xuid is missing!');

return this.xuid;
return this.xuid || '';
}

public getWindows(): WindowManager {
Expand Down Expand Up @@ -496,33 +486,36 @@ export default class Player extends Human {
* @param {object} options - The options to set the position.
* @param {Vector3} options.position - The new position.
* @param {MovementType} [options.type=MovementType.Normal] - The movement type.
* @param {number} [options.yaw=this.yaw] - The new yaw.
* @param {number} [options.pitch=this.pitch] - The new pitch.
* @param {number} [options.yaw=this.yaw] - The new yaw.
* @param {number} [options.headYaw=this.headYaw] - The new head yaw.
* @remarks This will notify the player's client about the position change.
*/
public async setPosition({
position,
type = MovementType.Normal,
pitch = this.pitch,
yaw = this.yaw,
pitch = this.pitch
headYaw = this.headYaw
}: {
position: Vector3;
type?: MovementType;
yaw?: number;
pitch?: number;
yaw?: number;
headYaw?: number;
}) {
this.yaw = yaw;
this.pitch = pitch;
this.yaw = yaw;
this.headYaw = headYaw;

await super.setPosition({ position });
await this.networkSession.broadcastMove(this, type);
await this.getNetworkSession().broadcastMove(this, type);

This comment has been minimized.

Copy link
@enricoangelon

enricoangelon Apr 16, 2024

Collaborator

Accessing the properties of the class directly when you are already inside it is better, as you know what you are doing and you avoid calling a getter that returns the same property, it becomes one less call, and may help the performance (for a small part 😄 )

}
/**
* Send the position to all the players in the same world.
* @returns {Promise<void>} A promise that resolves when the position is sent.
*/
public async sendPosition(): Promise<void> {
await this.networkSession.broadcastMove(this);
await super.sendPosition();
}

Expand Down
51 changes: 29 additions & 22 deletions packages/prismarine/src/entity/Entity.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,10 @@ export class EntityLike extends Position {
protected readonly runtimeId: bigint;
protected readonly server: Server;

public pitch = 0;
public yaw = 0;
public headYaw = 0;

/**
* EntityLike constructor.
* @constructor
Expand Down Expand Up @@ -286,22 +290,17 @@ export class Entity extends EntityLike {
* @returns {Promise<void>} A promise that resolves when the entity is spawned.
*/
public async sendSpawn(player?: Player): Promise<void> {
const players: Player[] = player
? [player]
: (this.getWorld()
.getEntities()
.filter((entity) => entity.isPlayer()) as Player[]);
const players: Player[] = player ? [player] : this.getWorld().getPlayers();

const packet = new AddActorPacket();
packet.runtimeEntityId = this.getRuntimeId();
packet.type = (this.constructor as any).MOB_ID; // TODO
packet.position = this;
// TODO: motion
packet.motion = new Vector3(0, 0, 0);
packet.pitch = 0;
packet.yaw = 0;
packet.headYaw = 0;
packet.metadata = this.metadata.getData();
packet.position = this.getPosition();
packet.motion = new Vector3(0, 0, 0); // TODO: motion
packet.pitch = this.pitch;
packet.yaw = this.yaw;
packet.headYaw = this.headYaw;
packet.metadata = this.metadata;
await Promise.all(players.map(async (p) => p.getNetworkSession().getConnection().sendDataPacket(packet)));
}

Expand All @@ -311,11 +310,7 @@ export class Entity extends EntityLike {
* @returns {Promise<void>} A promise that resolves when the entity is despawned.
*/
public async sendDespawn(player?: Player): Promise<void> {
const players: Player[] = player
? [player]
: (this.getWorld()
.getEntities()
.filter((entity) => entity.isPlayer()) as Player[]);
const players: Player[] = player ? [player] : this.getWorld().getPlayers();

const packet = new RemoveActorPacket();
packet.uniqueEntityId = this.runtimeId;
Expand All @@ -328,10 +323,8 @@ export class Entity extends EntityLike {
*/
public async sendPosition(): Promise<void> {
await Promise.all(
this.getServer()
.getSessionManager()
.getAllPlayers()
.filter((player) => player.getWorld().getUUID() === this.getWorld().getUUID())
this.getWorld()
.getPlayers()
.map(async (player) => {
const packet = new MoveActorAbsolutePacket();
packet.runtimeEntityId = this.runtimeId;
Expand Down Expand Up @@ -415,7 +408,21 @@ export class Entity extends EntityLike {
* @param {Vector3} position - The position.
* @returns {Promise<void>} A promise that resolves when the position is set.
*/
public async setPosition({ position }: { position: Vector3 }): Promise<void> {
public async setPosition({
position,
pitch = this.pitch,
yaw = this.yaw,
headYaw = this.headYaw
}: {
position: Vector3;
pitch?: number;
yaw?: number;
headYaw?: number;
}): Promise<void> {
this.pitch = pitch;
this.yaw = yaw;
this.headYaw = headYaw;

await super.setX(position.getX());
await super.setY(position.getY());
await super.setZ(position.getZ());
Expand Down
6 changes: 6 additions & 0 deletions packages/prismarine/src/entity/Metadata.ts
Original file line number Diff line number Diff line change
Expand Up @@ -160,6 +160,12 @@ export class MetadataWriter {
case FlagType.SHORT:
stream.writeUnsignedShortLE(value[1] as number);
break;
case FlagType.ITEM: // TODO: Implement this.
break;
case FlagType.POSITION: // TODO: Implement this.
break;
case FlagType.VECTOR: // TODO: Implement this.
break;
default:
throw new Error(`Metadata type ${value[0]} not supported`);
}
Expand Down
4 changes: 2 additions & 2 deletions packages/prismarine/src/math/Vector3.ts
Original file line number Diff line number Diff line change
Expand Up @@ -40,8 +40,8 @@ export default class Vector3 {
return `x: §b${this.x.toFixed(2)}§r, y: §b${this.y.toFixed(2)}§r, z: §b${this.z.toFixed(2)}§r`;
}

public static fromObject(obj: { x: number; y: number; z: number }): Vector3 {
return new Vector3(obj.x, obj.y, obj.z);
public static fromObject({ x, y, z }: { x: number; y: number; z: number }): Vector3 {
return new Vector3(x, y, z);
}

/**
Expand Down
2 changes: 0 additions & 2 deletions packages/prismarine/src/network/Packets.ts
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,6 @@ import SetTimePacket from './packet/SetTimePacket';
import SetTitlePacket from './packet/SetTitlePacket';
import ShowCreditsPacket from './packet/ShowCreditsPacket';
import ShowProfilePacket from './packet/ShowProfilePacket';
import ShowStoreOfferPacket from './packet/ShowStoreOfferPacket';
import StartGamePacket from './packet/StartGamePacket';
import TextPacket from './packet/TextPacket';
import TickSyncPacket from './packet/TickSyncPacket';
Expand Down Expand Up @@ -121,7 +120,6 @@ export {
SetTitlePacket,
ShowCreditsPacket,
ShowProfilePacket,
ShowStoreOfferPacket,
StartGamePacket,
TextPacket,
TickSyncPacket,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,6 @@ import type { PlayerSession } from '../../';
import type Server from '../../Server';
import { BlockMappings } from '../../block/BlockMappings';
import type ContainerEntry from '../../inventory/ContainerEntry';
import Vector3 from '../../math/Vector3';
import { Gamemode } from '../../world/';
import Identifiers from '../Identifiers';
import type PacketHandler from './PacketHandler';
Expand Down Expand Up @@ -87,17 +86,9 @@ export default class InventoryTransactionHandler implements PacketHandler<Invent
case UseItemAction.CLICK_AIR:
break;
case UseItemAction.BREAK_BLOCK: {
const chunk = await player
.getWorld()
.getChunkAt(useItemData.blockPosition.getX(), useItemData.blockPosition.getZ());

const chunkPos = new Vector3(
useItemData.blockPosition.getX(),
useItemData.blockPosition.getY(),
useItemData.blockPosition.getZ()
);
const chunk = await player.getWorld().getChunkAt(useItemData.blockPosition);

const blockId = chunk.getBlock(chunkPos.getX(), chunkPos.getY(), chunkPos.getZ());
const blockId = chunk.getBlock(useItemData.blockPosition);
const block = server.getBlockManager().getBlockByIdAndMeta(blockId.id, blockId.meta);
if (!block) return;

Expand All @@ -120,6 +111,7 @@ export default class InventoryTransactionHandler implements PacketHandler<Invent
.map(async (player) => player.getNetworkSession().getConnection().sendDataPacket(pk))
);

const chunkPos = useItemData.blockPosition;
chunk.setBlock(
chunkPos.getX(),
chunkPos.getY(),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ describe('network', () => {
getWorldManager: () => ({
getDefaultWorld: () => ({
addEntity: () => {},
getPlayers: () => [],
getPlayerData(_player: any) {
return { position: { x: 0, y: 0, z: 0 }, inventory: [] };
}
Expand Down
49 changes: 4 additions & 45 deletions packages/prismarine/src/network/packet/AddActorPacket.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import type { MetadataContainer } from '../../entity/Metadata';
import type { Metadata } from '../../entity/Metadata';
import Vector3 from '../../math/Vector3';
import Identifiers from '../Identifiers';
import { NetworkUtil } from '../NetworkUtil';
Expand Down Expand Up @@ -33,7 +33,7 @@ export default class AddActorPacket extends DataPacket {
public headYaw!: number;

public attributes = [];
public metadata!: MetadataContainer;
public metadata!: Metadata;
public links = [];

public encodePayload(): void {
Expand All @@ -55,53 +55,12 @@ export default class AddActorPacket extends DataPacket {
this.writeFloatLE(this.headYaw);
this.writeFloatLE(this.yaw); // bodyYaw

// TODO: attributes
this.writeUnsignedVarInt(this.attributes.length);

// TODO: fixme
// const metadata = Array.from(this.metadata);
this.writeUnsignedVarInt(/* metadata.length */ 0);
this.writeUnsignedVarInt(0); // TODO: attributes.
this.metadata.networkSerialize(this);

this.writeUnsignedVarInt(0); // ? unknown
this.writeUnsignedVarInt(0); // ? unknown

/* metadata.forEach(([key, [type, value]]) => {
this.writeUnsignedVarInt(key);
this.writeUnsignedVarInt(type);
switch (type) {
case FlagType.BYTE:
this.writeByte(value as number);
break;
case FlagType.SHORT:
this.writeShort(value as number);
break;
case FlagType.INT:
this.writeVarInt(value as number);
break;
case FlagType.FLOAT:
this.writeFloat(value as number);
break;
case FlagType.STRING:
this.writeString(value as string);
break;
case FlagType.ITEM:
// TODO:
break;
case FlagType.POSITION:
// TODO:
break;
case FlagType.LONG:
this.writeLong(value as bigint);
break;
case FlagType.VECTOR:
// TODO:
break;
default:
throw new Error(`Invalid type: ${type}`);
}
}); */

// TODO: links
this.writeUnsignedVarInt(this.links.length);
}
Expand Down

0 comments on commit 07bc6d0

Please sign in to comment.