diff --git a/Database Updates/007_PackageRateLimit.sql b/Database Updates/007_PackageRateLimit.sql index 00ca631d..0e6ffbc8 100644 --- a/Database Updates/007_PackageRateLimit.sql +++ b/Database Updates/007_PackageRateLimit.sql @@ -1 +1,3 @@ -INSERT INTO emulator_settings (`key`, `value`) VALUES ('packet.global.rate.limit', '50'); \ No newline at end of file +INSERT INTO emulator_settings (`key`, `value`) VALUES ('packet.global.rate.limit', '50'); + +ALTER TABLE `rooms` ADD COLUMN IF NOT EXISTS `youtube_enabled` TINYINT(1) NOT NULL DEFAULT 0; \ No newline at end of file diff --git a/Emulator/src/main/java/com/eu/habbo/habbohotel/rooms/Room.java b/Emulator/src/main/java/com/eu/habbo/habbohotel/rooms/Room.java index ac11d120..af8c9b29 100644 --- a/Emulator/src/main/java/com/eu/habbo/habbohotel/rooms/Room.java +++ b/Emulator/src/main/java/com/eu/habbo/habbohotel/rooms/Room.java @@ -178,27 +178,30 @@ public class Room implements Comparable, ISerialize, Runnable { // YouTube room broadcast state: tracks the current video being broadcast // by the room owner, the owner's playlist, and which users have the player open. + private boolean youtubeEnabled = false; private String youtubeCurrentVideo = ""; private String youtubeSenderName = ""; private final java.util.List youtubePlaylist = new java.util.concurrent.CopyOnWriteArrayList<>(); private final java.util.Set youtubeWatchers = java.util.concurrent.ConcurrentHashMap.newKeySet(); + public boolean isYoutubeEnabled() { return this.youtubeEnabled; } + public void setYoutubeEnabled(boolean enabled) { this.youtubeEnabled = enabled; } public String getYoutubeCurrentVideo() { return this.youtubeCurrentVideo; } public String getYoutubeSenderName() { return this.youtubeSenderName; } public java.util.List getYoutubePlaylist() { return this.youtubePlaylist; } public java.util.Set getYoutubeWatchers() { return this.youtubeWatchers; } public void setYoutubeVideo(String videoId, String senderName, java.util.List playlist) { - this.youtubeCurrentVideo = videoId; - this.youtubeSenderName = senderName; - this.youtubePlaylist.clear(); - if (playlist != null) this.youtubePlaylist.addAll(playlist); + this.youtubeCurrentVideo = videoId; + this.youtubeSenderName = senderName; + this.youtubePlaylist.clear(); + if (playlist != null) this.youtubePlaylist.addAll(playlist); } public void clearYoutubeVideo() { - this.youtubeCurrentVideo = ""; - this.youtubeSenderName = ""; - this.youtubePlaylist.clear(); + this.youtubeCurrentVideo = ""; + this.youtubeSenderName = ""; + this.youtubePlaylist.clear(); } public final THashMap cache; @@ -228,6 +231,7 @@ public class Room implements Comparable, ISerialize, Runnable { this.allowPetsEat = set.getBoolean("allow_other_pets_eat"); this.allowWalkthrough = set.getBoolean("allow_walkthrough"); this.hideWall = set.getBoolean("allow_hidewall"); + try { this.youtubeEnabled = set.getBoolean("youtube_enabled"); } catch (Exception e) { this.youtubeEnabled = false; } this.chatMode = set.getInt("chat_mode"); this.chatWeight = set.getInt("chat_weight"); this.chatSpeed = set.getInt("chat_speed"); @@ -410,7 +414,7 @@ public class Room implements Comparable, ISerialize, Runnable { if (this.loaded || this.loadingInProgress || !this.preLoaded) { return; } - + this.loadingInProgress = true; this.loadingFuture = CompletableFuture.runAsync(() -> { this.loadDataInternal(); @@ -430,7 +434,7 @@ public class Room implements Comparable, ISerialize, Runnable { } future = this.loadingFuture; } - + if (future != null) { try { future.join(); @@ -445,7 +449,7 @@ public class Room implements Comparable, ISerialize, Runnable { public void loadData() { CompletableFuture futureToWait = null; boolean shouldLoad = false; - + synchronized (this.loadLock) { if (this.loadingInProgress) { // Get the future to wait on outside the lock @@ -455,7 +459,7 @@ public class Room implements Comparable, ISerialize, Runnable { shouldLoad = true; } } - + // Wait for existing load outside the lock if (futureToWait != null) { try { @@ -465,7 +469,7 @@ public class Room implements Comparable, ISerialize, Runnable { } return; } - + // Load if needed if (shouldLoad) { this.loadDataInternal(); @@ -505,7 +509,7 @@ public class Room implements Comparable, ISerialize, Runnable { CompletableFuture.runAsync(() -> { try (Connection promoConnection = Emulator.getDatabase().getDataSource().getConnection(); PreparedStatement stmt = promoConnection.prepareStatement( - "SELECT * FROM room_promotions WHERE room_id = ? AND end_timestamp > ? LIMIT 1")) { + "SELECT * FROM room_promotions WHERE room_id = ? AND end_timestamp > ? LIMIT 1")) { stmt.setInt(1, this.id); stmt.setInt(2, Emulator.getIntUnixTimestamp()); try (ResultSet promoSet = stmt.executeQuery()) { @@ -600,7 +604,7 @@ public class Room implements Comparable, ISerialize, Runnable { } this.roomCycleTask = Emulator.getThreading().getService() - .scheduleAtFixedRate(this, 500, 500, TimeUnit.MILLISECONDS); + .scheduleAtFixedRate(this, 500, 500, TimeUnit.MILLISECONDS); } catch (Exception e) { LOGGER.error("Caught exception during room load", e); } @@ -619,7 +623,7 @@ public class Room implements Comparable, ISerialize, Runnable { item.setExtradata("1"); this.updateItem(item); } - + // Set loaded flag with lock synchronized (this.loadLock) { this.loaded = true; @@ -636,7 +640,7 @@ public class Room implements Comparable, ISerialize, Runnable { this.layout = Emulator.getGameEnvironment().getRoomManager().loadCustomLayout(this); } else { this.layout = Emulator.getGameEnvironment().getRoomManager() - .loadLayout(this.layoutName, this); + .loadLayout(this.layoutName, this); } } } @@ -668,7 +672,7 @@ public class Room implements Comparable, ISerialize, Runnable { this.unitManager.clearBots(); try (PreparedStatement statement = connection.prepareStatement( - "SELECT users.username AS owner_name, bots.* FROM bots INNER JOIN users ON bots.user_id = users.id WHERE room_id = ?")) { + "SELECT users.username AS owner_name, bots.* FROM bots INNER JOIN users ON bots.user_id = users.id WHERE room_id = ?")) { statement.setInt(1, this.id); try (ResultSet set = statement.executeQuery()) { while (set.next()) { @@ -679,11 +683,11 @@ public class Room implements Comparable, ISerialize, Runnable { b.setRoomUnit(new RoomUnit()); b.getRoomUnit().setPathFinderRoom(this); b.getRoomUnit() - .setLocation(this.layout.getTile((short) set.getInt("x"), (short) set.getInt("y"))); + .setLocation(this.layout.getTile((short) set.getInt("x"), (short) set.getInt("y"))); if (b.getRoomUnit().getCurrentLocation() == null) { b.getRoomUnit().setLocation(this.getLayout().getDoorTile()); b.getRoomUnit() - .setRotation(RoomUserRotation.fromValue(this.getLayout().getDoorDirection())); + .setRotation(RoomUserRotation.fromValue(this.getLayout().getDoorDirection())); } else { b.getRoomUnit().setZ(set.getDouble("z")); b.getRoomUnit().setPreviousLocationZ(set.getDouble("z")); @@ -707,7 +711,7 @@ public class Room implements Comparable, ISerialize, Runnable { this.unitManager.clearPets(); try (PreparedStatement statement = connection.prepareStatement( - "SELECT users.username as pet_owner_name, users_pets.* FROM users_pets INNER JOIN users ON users_pets.user_id = users.id WHERE room_id = ?")) { + "SELECT users.username as pet_owner_name, users_pets.* FROM users_pets INNER JOIN users ON users_pets.user_id = users.id WHERE room_id = ?")) { statement.setInt(1, this.id); try (ResultSet set = statement.executeQuery()) { while (set.next()) { @@ -717,11 +721,11 @@ public class Room implements Comparable, ISerialize, Runnable { pet.setRoomUnit(new RoomUnit()); pet.getRoomUnit().setPathFinderRoom(this); pet.getRoomUnit() - .setLocation(this.layout.getTile((short) set.getInt("x"), (short) set.getInt("y"))); + .setLocation(this.layout.getTile((short) set.getInt("x"), (short) set.getInt("y"))); if (pet.getRoomUnit().getCurrentLocation() == null) { pet.getRoomUnit().setLocation(this.getLayout().getDoorTile()); pet.getRoomUnit() - .setRotation(RoomUserRotation.fromValue(this.getLayout().getDoorDirection())); + .setRotation(RoomUserRotation.fromValue(this.getLayout().getDoorDirection())); } else { pet.getRoomUnit().setZ(set.getDouble("z")); pet.getRoomUnit().setRotation(RoomUserRotation.values()[set.getInt("rot")]); @@ -793,7 +797,7 @@ public class Room implements Comparable, ISerialize, Runnable { THashSet updatedTiles = new THashSet<>(); Rectangle rectangle = RoomLayout.getRectangle(item.getX(), item.getY(), - item.getBaseItem().getWidth(), item.getBaseItem().getLength(), item.getRotation()); + item.getBaseItem().getWidth(), item.getBaseItem().getLength(), item.getRotation()); for (short x = (short) rectangle.x; x < rectangle.x + rectangle.getWidth(); x++) { for (short y = (short) rectangle.y; y < rectangle.y + rectangle.getHeight(); y++) { @@ -817,7 +821,7 @@ public class Room implements Comparable, ISerialize, Runnable { } Habbo habbo = (picker != null && picker.getHabboInfo().getId() == item.getId() ? picker - : Emulator.getGameServer().getGameClientManager().getHabbo(item.getUserId())); + : Emulator.getGameServer().getGameClientManager().getHabbo(item.getUserId())); if (habbo != null) { habbo.getInventory().getItemsComponent().addItem(item); habbo.getClient().sendResponse(new AddHabboItemComposer(item)); @@ -1055,7 +1059,7 @@ public class Room implements Comparable, ISerialize, Runnable { message.appendInt(this.category); String[] tags = Arrays.stream(this.tags.split(";")).filter(t -> !t.isEmpty()) - .toArray(String[]::new); + .toArray(String[]::new); message.appendInt(tags.length); for (String s : tags) { message.appendString(s); @@ -1119,8 +1123,8 @@ public class Room implements Comparable, ISerialize, Runnable { public void save() { if (this.needsUpdate) { try (Connection connection = Emulator.getDatabase().getDataSource() - .getConnection(); PreparedStatement statement = connection.prepareStatement( - "UPDATE rooms SET name = ?, description = ?, password = ?, state = ?, users_max = ?, category = ?, score = ?, paper_floor = ?, paper_wall = ?, paper_landscape = ?, thickness_wall = ?, wall_height = ?, thickness_floor = ?, moodlight_data = ?, tags = ?, allow_other_pets = ?, allow_other_pets_eat = ?, allow_walkthrough = ?, allow_hidewall = ?, chat_mode = ?, chat_weight = ?, chat_speed = ?, chat_hearing_distance = ?, chat_protection =?, who_can_mute = ?, who_can_kick = ?, who_can_ban = ?, poll_id = ?, guild_id = ?, roller_speed = ?, override_model = ?, is_staff_picked = ?, promoted = ?, trade_mode = ?, move_diagonally = ?, owner_id = ?, owner_name = ?, jukebox_active = ?, hidewired = ?, allow_underpass = ? WHERE id = ?")) { + .getConnection(); PreparedStatement statement = connection.prepareStatement( + "UPDATE rooms SET name = ?, description = ?, password = ?, state = ?, users_max = ?, category = ?, score = ?, paper_floor = ?, paper_wall = ?, paper_landscape = ?, thickness_wall = ?, wall_height = ?, thickness_floor = ?, moodlight_data = ?, tags = ?, allow_other_pets = ?, allow_other_pets_eat = ?, allow_walkthrough = ?, allow_hidewall = ?, chat_mode = ?, chat_weight = ?, chat_speed = ?, chat_hearing_distance = ?, chat_protection =?, who_can_mute = ?, who_can_kick = ?, who_can_ban = ?, poll_id = ?, guild_id = ?, roller_speed = ?, override_model = ?, is_staff_picked = ?, promoted = ?, trade_mode = ?, move_diagonally = ?, owner_id = ?, owner_name = ?, jukebox_active = ?, hidewired = ?, allow_underpass = ?, youtube_enabled = ? WHERE id = ?")) { statement.setString(1, this.name); statement.setString(2, this.description); statement.setString(3, this.password); @@ -1170,7 +1174,8 @@ public class Room implements Comparable, ISerialize, Runnable { statement.setString(38, this.jukeboxActive ? "1" : "0"); statement.setString(39, this.hideWired ? "1" : "0"); statement.setString(40, this.allowUnderpass ? "1" : "0"); - statement.setInt(41, this.id); + statement.setString(41, this.youtubeEnabled ? "1" : "0"); + statement.setInt(42, this.id); statement.executeUpdate(); this.needsUpdate = false; } catch (SQLException e) { @@ -1185,8 +1190,8 @@ public class Room implements Comparable, ISerialize, Runnable { */ public void updateDatabaseUserCount() { try (Connection connection = Emulator.getDatabase().getDataSource() - .getConnection(); PreparedStatement statement = connection.prepareStatement( - "UPDATE rooms SET users = ? WHERE id = ? LIMIT 1")) { + .getConnection(); PreparedStatement statement = connection.prepareStatement( + "UPDATE rooms SET users = ? WHERE id = ? LIMIT 1")) { statement.setInt(1, this.getUserCount()); statement.setInt(2, this.id); statement.executeUpdate(); @@ -1500,7 +1505,7 @@ public class Room implements Comparable, ISerialize, Runnable { if (extraData.length == 4) { if (extraData[0].equalsIgnoreCase("1")) { return Color.getHSBColor(Integer.parseInt(extraData[1]), - Integer.parseInt(extraData[2]), Integer.parseInt(extraData[3])); + Integer.parseInt(extraData[2]), Integer.parseInt(extraData[3])); } } } @@ -1607,7 +1612,7 @@ public class Room implements Comparable, ISerialize, Runnable { public String[] filterAnything() { return new String[]{this.getOwnerName(), this.getGuildName(), this.getDescription(), - this.getPromotionDesc()}; + this.getPromotionDesc()}; } public long getCycleTimestamp() { @@ -1809,7 +1814,17 @@ public class Room implements Comparable, ISerialize, Runnable { } private void cleanupYoutubeWatcher(Habbo habbo) { - if (habbo != null && this.youtubeWatchers.remove(habbo.getHabboInfo().getId())) { + if (habbo == null) return; + int userId = habbo.getHabboInfo().getId(); + + // If the broadcast sender leaves, stop the broadcast for everyone + if (!this.youtubeCurrentVideo.isEmpty() + && habbo.getHabboInfo().getUsername().equals(this.youtubeSenderName)) { + this.clearYoutubeVideo(); + this.sendComposer(new com.eu.habbo.messages.outgoing.rooms.youtube.YouTubeRoomBroadcastComposer("", "", java.util.Collections.emptyList()).compose()); + } + + if (this.youtubeWatchers.remove(userId)) { this.sendComposer(new com.eu.habbo.messages.outgoing.rooms.youtube.YouTubeRoomWatchersComposer(this.youtubeWatchers).compose()); } } @@ -1949,7 +1964,7 @@ public class Room implements Comparable, ISerialize, Runnable { } public void talk(final Habbo habbo, final RoomChatMessage roomChatMessage, RoomChatType chatType, - boolean ignoreWired) { + boolean ignoreWired) { this.chatManager.talk(habbo, roomChatMessage, chatType, ignoreWired); } @@ -2094,7 +2109,7 @@ public class Room implements Comparable, ISerialize, Runnable { private void loadRights(Connection connection) { this.rights.clear(); try (PreparedStatement statement = connection.prepareStatement( - "SELECT user_id FROM room_rights WHERE room_id = ?")) { + "SELECT user_id FROM room_rights WHERE room_id = ?")) { statement.setInt(1, this.id); try (ResultSet set = statement.executeQuery()) { while (set.next()) { @@ -2110,7 +2125,7 @@ public class Room implements Comparable, ISerialize, Runnable { this.bannedHabbos.clear(); try (PreparedStatement statement = connection.prepareStatement( - "SELECT users.username, users.id, room_bans.* FROM room_bans INNER JOIN users ON room_bans.user_id = users.id WHERE ends > ? AND room_bans.room_id = ?")) { + "SELECT users.username, users.id, room_bans.* FROM room_bans INNER JOIN users ON room_bans.user_id = users.id WHERE ends > ? AND room_bans.room_id = ?")) { statement.setInt(1, Emulator.getIntUnixTimestamp()); statement.setInt(2, this.id); try (ResultSet set = statement.executeQuery()) { @@ -2132,7 +2147,7 @@ public class Room implements Comparable, ISerialize, Runnable { Guild guild = Emulator.getGameEnvironment().getGuildManager().getGuild(this.guild); if (Emulator.getGameEnvironment().getGuildManager().getOnlyAdmins(guild) - .get(habbo.getHabboInfo().getId()) != null) { + .get(habbo.getHabboInfo().getId()) != null) { return RoomRightLevels.GUILD_ADMIN; } @@ -2210,15 +2225,15 @@ public class Room implements Comparable, ISerialize, Runnable { } if (habbo.getRoomUnit().hasStatus(RoomUnitStatus.SIT) || !habbo.getRoomUnit() - .canForcePosture()) { + .canForcePosture()) { return; } this.dance(habbo, DanceType.NONE); habbo.getRoomUnit().cmdSit = true; habbo.getRoomUnit().setBodyRotation( - RoomUserRotation.values()[habbo.getRoomUnit().getBodyRotation().getValue() - - habbo.getRoomUnit().getBodyRotation().getValue() % 2]); + RoomUserRotation.values()[habbo.getRoomUnit().getBodyRotation().getValue() + - habbo.getRoomUnit().getBodyRotation().getValue() % 2]); habbo.getRoomUnit().setStatus(RoomUnitStatus.SIT, 0.5 + ""); this.sendComposer(new RoomUserStatusComposer(habbo.getRoomUnit()).compose()); WiredManager.triggerUserPerformsAction(this, habbo.getRoomUnit(), WiredUserActionType.SIT, -1); @@ -2232,11 +2247,11 @@ public class Room implements Comparable, ISerialize, Runnable { HabboItem item = this.getTopItemAt(habbo.getRoomUnit().getX(), habbo.getRoomUnit().getY()); if (item == null || !item.getBaseItem().allowSit() || !item.getBaseItem().allowLay()) { boolean wasSittingOrLaying = habbo.getRoomUnit().hasStatus(RoomUnitStatus.SIT) - || habbo.getRoomUnit().hasStatus(RoomUnitStatus.LAY); + || habbo.getRoomUnit().hasStatus(RoomUnitStatus.LAY); habbo.getRoomUnit().cmdStand = true; habbo.getRoomUnit().setBodyRotation( - RoomUserRotation.values()[habbo.getRoomUnit().getBodyRotation().getValue() - - habbo.getRoomUnit().getBodyRotation().getValue() % 2]); + RoomUserRotation.values()[habbo.getRoomUnit().getBodyRotation().getValue() + - habbo.getRoomUnit().getBodyRotation().getValue() % 2]); habbo.getRoomUnit().removeStatus(RoomUnitStatus.SIT); habbo.getRoomUnit().removeStatus(RoomUnitStatus.LAY); this.sendComposer(new RoomUserStatusComposer(habbo.getRoomUnit()).compose()); @@ -2270,9 +2285,9 @@ public class Room implements Comparable, ISerialize, Runnable { if (item.getBaseItem().getType() == FurnitureType.FLOOR) { this.sendComposer(new FloorItemUpdateComposer(item).compose()); this.updateTiles(this.getLayout() - .getTilesAt(this.layout.getTile(item.getX(), item.getY()), - item.getBaseItem().getWidth(), item.getBaseItem().getLength(), - item.getRotation())); + .getTilesAt(this.layout.getTile(item.getX(), item.getY()), + item.getBaseItem().getWidth(), item.getBaseItem().getLength(), + item.getRotation())); } else if (item.getBaseItem().getType() == FurnitureType.WALL) { this.sendComposer(new WallItemUpdateComposer(item).compose()); } @@ -2294,8 +2309,8 @@ public class Room implements Comparable, ISerialize, Runnable { } this.updateTiles(this.getLayout() - .getTilesAt(this.layout.getTile(item.getX(), item.getY()), item.getBaseItem().getWidth(), - item.getBaseItem().getLength(), item.getRotation())); + .getTilesAt(this.layout.getTile(item.getX(), item.getY()), item.getBaseItem().getWidth(), + item.getBaseItem().getLength(), item.getRotation())); if (item instanceof InteractionMultiHeight) { ((InteractionMultiHeight) item).updateUnitsOnItem(this); @@ -2332,18 +2347,18 @@ public class Room implements Comparable, ISerialize, Runnable { public void refreshGuild(Guild guild) { if (guild.getRoomId() == this.id) { THashSet members = Emulator.getGameEnvironment().getGuildManager() - .getGuildMembers(guild.getId()); + .getGuildMembers(guild.getId()); for (Habbo habbo : this.getHabbos()) { Optional member = members.stream() - .filter(m -> m.getUserId() == habbo.getHabboInfo().getId()).findAny(); + .filter(m -> m.getUserId() == habbo.getHabboInfo().getId()).findAny(); if (!member.isPresent()) { continue; } habbo.getClient() - .sendResponse(new GuildInfoComposer(guild, habbo.getClient(), false, member.get())); + .sendResponse(new GuildInfoComposer(guild, habbo.getClient(), false, member.get())); } } @@ -2378,7 +2393,7 @@ public class Room implements Comparable, ISerialize, Runnable { if (habbo.getHabboInfo().getCurrentRoom() == this) { if (habbo.getHabboInfo().getId() != this.ownerId) { if (!(habbo.hasPermission(Permission.ACC_ANYROOMOWNER) || habbo.hasPermission( - Permission.ACC_MOVEROTATE))) { + Permission.ACC_MOVEROTATE))) { this.refreshRightsForHabbo(habbo); } } @@ -2464,18 +2479,18 @@ public class Room implements Comparable, ISerialize, Runnable { } } else { this.sendComposer(new RoomFloorItemsComposer(this.itemManager.getFurniOwnerNames(), - this.roomSpecialTypes.getTriggers()).compose()); + this.roomSpecialTypes.getTriggers()).compose()); this.sendComposer(new RoomFloorItemsComposer(this.itemManager.getFurniOwnerNames(), - this.roomSpecialTypes.getEffects()).compose()); + this.roomSpecialTypes.getEffects()).compose()); this.sendComposer(new RoomFloorItemsComposer(this.itemManager.getFurniOwnerNames(), - this.roomSpecialTypes.getConditions()).compose()); + this.roomSpecialTypes.getConditions()).compose()); this.sendComposer(new RoomFloorItemsComposer(this.itemManager.getFurniOwnerNames(), - this.roomSpecialTypes.getExtras()).compose()); + this.roomSpecialTypes.getExtras()).compose()); } } public FurnitureMovementError canPlaceFurnitureAt(HabboItem item, Habbo habbo, RoomTile tile, - int rotation) { + int rotation) { return this.itemManager.canPlaceFurnitureAt(item, habbo, tile, rotation); } @@ -2484,17 +2499,17 @@ public class Room implements Comparable, ISerialize, Runnable { } public FurnitureMovementError furnitureFitsAt(RoomTile tile, HabboItem item, int rotation, - boolean checkForUnits) { + boolean checkForUnits) { return this.itemManager.furnitureFitsAt(tile, item, rotation, checkForUnits); } public FurnitureMovementError furnitureFitsAtWithPhysics(RoomTile tile, HabboItem item, int rotation, - boolean checkForUnits, WiredMovementPhysics physics) { + boolean checkForUnits, WiredMovementPhysics physics) { return this.itemManager.furnitureFitsAtWithPhysics(tile, item, rotation, checkForUnits, physics); } public FurnitureMovementError placeFloorFurniAt(HabboItem item, RoomTile tile, int rotation, - Habbo owner) { + Habbo owner) { return this.itemManager.placeFloorFurniAt(item, tile, rotation, owner); } @@ -2503,17 +2518,17 @@ public class Room implements Comparable, ISerialize, Runnable { } public FurnitureMovementError moveFurniTo(HabboItem item, RoomTile tile, int rotation, - Habbo actor) { + Habbo actor) { return this.itemManager.moveFurniTo(item, tile, rotation, actor); } public FurnitureMovementError moveFurniTo(HabboItem item, RoomTile tile, int rotation, - Habbo actor, boolean sendUpdates) { + Habbo actor, boolean sendUpdates) { return this.itemManager.moveFurniTo(item, tile, rotation, actor, sendUpdates); } public FurnitureMovementError moveFurniTo(HabboItem item, RoomTile tile, int rotation, - Habbo actor, boolean sendUpdates, boolean checkForUnits) { + Habbo actor, boolean sendUpdates, boolean checkForUnits) { return this.itemManager.moveFurniTo(item, tile, rotation, actor, sendUpdates, checkForUnits); } @@ -2530,12 +2545,12 @@ public class Room implements Comparable, ISerialize, Runnable { } public FurnitureMovementError moveFurniToWithPhysics(HabboItem item, RoomTile tile, int rotation, - Habbo actor, boolean sendUpdates, boolean checkForUnits, WiredMovementPhysics physics) { + Habbo actor, boolean sendUpdates, boolean checkForUnits, WiredMovementPhysics physics) { return this.itemManager.moveFurniToWithPhysics(item, tile, rotation, actor, sendUpdates, checkForUnits, physics); } public FurnitureMovementError moveFurniToWithPhysics(HabboItem item, RoomTile tile, int rotation, double z, - Habbo actor, boolean sendUpdates, boolean checkForUnits, WiredMovementPhysics physics) { + Habbo actor, boolean sendUpdates, boolean checkForUnits, WiredMovementPhysics physics) { return this.itemManager.moveFurniToWithPhysics(item, tile, rotation, z, actor, sendUpdates, checkForUnits, physics); } diff --git a/Emulator/src/main/java/com/eu/habbo/habbohotel/rooms/RoomManager.java b/Emulator/src/main/java/com/eu/habbo/habbohotel/rooms/RoomManager.java index 527cb759..a65aefa2 100644 --- a/Emulator/src/main/java/com/eu/habbo/habbohotel/rooms/RoomManager.java +++ b/Emulator/src/main/java/com/eu/habbo/habbohotel/rooms/RoomManager.java @@ -790,7 +790,6 @@ public class RoomManager { habbo.getRoomUnit().setInvisible(false); room.addHabbo(habbo); - // Pre-send own wearing badges so the client cache is populated before the user clicks themselves habbo.getClient().sendResponse(new UserBadgesComposer(habbo.getInventory().getBadgesComponent().getWearingBadges(), habbo.getHabboInfo().getId())); List habbos = new ArrayList<>(); @@ -987,6 +986,9 @@ public class RoomManager { } } + habbo.getClient().sendResponse(new com.eu.habbo.messages.outgoing.rooms.youtube.YouTubeRoomSettingsComposer( + room.isYoutubeEnabled()).compose()); + if (!room.getYoutubeCurrentVideo().isEmpty()) { habbo.getClient().sendResponse(new com.eu.habbo.messages.outgoing.rooms.youtube.YouTubeRoomBroadcastComposer( room.getYoutubeCurrentVideo(), diff --git a/Emulator/src/main/java/com/eu/habbo/messages/PacketManager.java b/Emulator/src/main/java/com/eu/habbo/messages/PacketManager.java index 5d6296dc..919450b8 100644 --- a/Emulator/src/main/java/com/eu/habbo/messages/PacketManager.java +++ b/Emulator/src/main/java/com/eu/habbo/messages/PacketManager.java @@ -681,5 +681,6 @@ public class PacketManager { // YouTube Room Broadcast this.registerHandler(Incoming.YouTubeRoomPlayEvent, com.eu.habbo.messages.incoming.rooms.youtube.YouTubeRoomPlayEvent.class); this.registerHandler(Incoming.YouTubeRoomWatchingEvent, com.eu.habbo.messages.incoming.rooms.youtube.YouTubeRoomWatchingEvent.class); + this.registerHandler(Incoming.YouTubeRoomSettingsEvent, com.eu.habbo.messages.incoming.rooms.youtube.YouTubeRoomSettingsEvent.class); } } diff --git a/Emulator/src/main/java/com/eu/habbo/messages/incoming/Incoming.java b/Emulator/src/main/java/com/eu/habbo/messages/incoming/Incoming.java index 5324b750..a85d54fc 100644 --- a/Emulator/src/main/java/com/eu/habbo/messages/incoming/Incoming.java +++ b/Emulator/src/main/java/com/eu/habbo/messages/incoming/Incoming.java @@ -440,4 +440,5 @@ public class Incoming { // YouTube Room Broadcast public static final int YouTubeRoomPlayEvent = 8001; public static final int YouTubeRoomWatchingEvent = 8002; + public static final int YouTubeRoomSettingsEvent = 8003; } diff --git a/Emulator/src/main/java/com/eu/habbo/messages/incoming/rooms/youtube/YouTubeRoomPlayEvent.java b/Emulator/src/main/java/com/eu/habbo/messages/incoming/rooms/youtube/YouTubeRoomPlayEvent.java index d5c5edf1..1dec152a 100644 --- a/Emulator/src/main/java/com/eu/habbo/messages/incoming/rooms/youtube/YouTubeRoomPlayEvent.java +++ b/Emulator/src/main/java/com/eu/habbo/messages/incoming/rooms/youtube/YouTubeRoomPlayEvent.java @@ -27,8 +27,7 @@ public class YouTubeRoomPlayEvent extends MessageHandler { Room room = habbo.getHabboInfo().getCurrentRoom(); if (room == null) return; - - // Only the room owner or users with rights can broadcast + if (!room.isYoutubeEnabled()) return; if (!room.isOwner(habbo) && !room.hasRights(habbo)) return; String videoId = this.packet.readString(); @@ -58,7 +57,7 @@ public class YouTubeRoomPlayEvent extends MessageHandler { // Broadcast to everyone in the room (empty videoId = stop) room.sendComposer( - new YouTubeRoomBroadcastComposer(videoId, habbo.getHabboInfo().getUsername(), playlist).compose() + new YouTubeRoomBroadcastComposer(videoId, habbo.getHabboInfo().getUsername(), playlist).compose() ); } } diff --git a/Emulator/src/main/java/com/eu/habbo/messages/incoming/rooms/youtube/YouTubeRoomSettingsEvent.java b/Emulator/src/main/java/com/eu/habbo/messages/incoming/rooms/youtube/YouTubeRoomSettingsEvent.java new file mode 100644 index 00000000..b3f8ceb5 --- /dev/null +++ b/Emulator/src/main/java/com/eu/habbo/messages/incoming/rooms/youtube/YouTubeRoomSettingsEvent.java @@ -0,0 +1,35 @@ +package com.eu.habbo.messages.incoming.rooms.youtube; + +import com.eu.habbo.habbohotel.rooms.Room; +import com.eu.habbo.habbohotel.users.Habbo; +import com.eu.habbo.messages.incoming.MessageHandler; +import com.eu.habbo.messages.outgoing.rooms.youtube.YouTubeRoomBroadcastComposer; +import com.eu.habbo.messages.outgoing.rooms.youtube.YouTubeRoomSettingsComposer; + +public class YouTubeRoomSettingsEvent extends MessageHandler { + + @Override + public int getRatelimit() { + return 200; + } + + @Override + public void handle() throws Exception { + Habbo habbo = this.client.getHabbo(); + if (habbo == null) return; + + Room room = habbo.getHabboInfo().getCurrentRoom(); + if (room == null) return; + if (!room.isOwner(habbo)) return; + + boolean enabled = this.packet.readInt() == 1; + room.setYoutubeEnabled(enabled); + room.setNeedsUpdate(true); + room.sendComposer(new YouTubeRoomSettingsComposer(enabled).compose()); + + if (!enabled && !room.getYoutubeCurrentVideo().isEmpty()) { + room.clearYoutubeVideo(); + room.sendComposer(new YouTubeRoomBroadcastComposer("", "", java.util.Collections.emptyList()).compose()); + } + } +} diff --git a/Emulator/src/main/java/com/eu/habbo/messages/outgoing/Outgoing.java b/Emulator/src/main/java/com/eu/habbo/messages/outgoing/Outgoing.java index bce53254..386bf3b3 100644 --- a/Emulator/src/main/java/com/eu/habbo/messages/outgoing/Outgoing.java +++ b/Emulator/src/main/java/com/eu/habbo/messages/outgoing/Outgoing.java @@ -574,5 +574,6 @@ public class Outgoing { // YouTube Room Broadcast public static final int YouTubeRoomBroadcastComposer = 8001; public static final int YouTubeRoomWatchersComposer = 8002; + public static final int YouTubeRoomSettingsComposer = 8003; } diff --git a/Emulator/src/main/java/com/eu/habbo/messages/outgoing/rooms/youtube/YouTubeRoomSettingsComposer.java b/Emulator/src/main/java/com/eu/habbo/messages/outgoing/rooms/youtube/YouTubeRoomSettingsComposer.java new file mode 100644 index 00000000..64ff91cb --- /dev/null +++ b/Emulator/src/main/java/com/eu/habbo/messages/outgoing/rooms/youtube/YouTubeRoomSettingsComposer.java @@ -0,0 +1,20 @@ +package com.eu.habbo.messages.outgoing.rooms.youtube; + +import com.eu.habbo.messages.ServerMessage; +import com.eu.habbo.messages.outgoing.MessageComposer; +import com.eu.habbo.messages.outgoing.Outgoing; + +public class YouTubeRoomSettingsComposer extends MessageComposer { + private final boolean youtubeEnabled; + + public YouTubeRoomSettingsComposer(boolean youtubeEnabled) { + this.youtubeEnabled = youtubeEnabled; + } + + @Override + protected ServerMessage composeInternal() { + this.response.init(Outgoing.YouTubeRoomSettingsComposer); + this.response.appendInt(this.youtubeEnabled ? 1 : 0); + return this.response; + } +}