diff --git a/README.md b/README.md index f96ea1a0..fe6c2c88 100644 --- a/README.md +++ b/README.md @@ -16,7 +16,7 @@ Arcturus Morningstar is as a fork of Arcturus Emulator by TheGeneral. Arcturus M [![image](https://img.shields.io/discord/557240155040251905?style=for-the-badge&logo=discord&color=7289DA&label=KREWS&logoColor=fff)](https://discord.gg/BzfFsTp) ## Download ## -[![image](https://img.shields.io/badge/STABLE%20RELEASES-3.5.3-success.svg?style=for-the-badge&logo=appveyor)](https://git.krews.org/morningstar/Arcturus-Community/-/releases) +[![image](https://img.shields.io/badge/STABLE%20RELEASES-3.5.4-success.svg?style=for-the-badge&logo=appveyor)](https://git.krews.org/morningstar/Arcturus-Community/-/releases) [![image](https://img.shields.io/badge/DEVELOPER%20BUILDS-4.0-red.svg?style=for-the-badge&logo=appveyor)](https://git.krews.org/morningstar/Arcturus-Community/-/jobs) * diff --git a/pom.xml b/pom.xml index b8b6b996..4a2fec2e 100644 --- a/pom.xml +++ b/pom.xml @@ -6,7 +6,7 @@ com.eu.habbo Habbo - 3.5.3 + 3.5.4 UTF-8 diff --git a/src/main/java/com/eu/habbo/Emulator.java b/src/main/java/com/eu/habbo/Emulator.java index f83cbc6f..d532cc1d 100644 --- a/src/main/java/com/eu/habbo/Emulator.java +++ b/src/main/java/com/eu/habbo/Emulator.java @@ -37,7 +37,7 @@ public final class Emulator { public final static int MAJOR = 3; public final static int MINOR = 5; - public final static int BUILD = 3; + public final static int BUILD = 4; public final static String PREVIEW = ""; public static final String version = "Arcturus Morningstar" + " " + MAJOR + "." + MINOR + "." + BUILD + " " + PREVIEW; @@ -49,7 +49,7 @@ public final class Emulator { "██║╚██╔╝██║██║ ██║██╔══██╗██║╚██╗██║██║██║╚██╗██║██║ ██║╚════██║ ██║ ██╔══██║██╔══██╗\n" + "██║ ╚═╝ ██║╚██████╔╝██║ ██║██║ ╚████║██║██║ ╚████║╚██████╔╝███████║ ██║ ██║ ██║██║ ██║\n" + "╚═╝ ╚═╝ ╚═════╝ ╚═╝ ╚═╝╚═╝ ╚═══╝╚═╝╚═╝ ╚═══╝ ╚═════╝ ╚══════╝ ╚═╝ ╚═╝ ╚═╝╚═╝ ╚═╝\n" + - "Still Rocking in 2023.\n"; + "Still Rocking in 2024.\n"; public static String build = ""; public static boolean isReady = false; diff --git a/src/main/java/com/eu/habbo/habbohotel/catalog/CatalogManager.java b/src/main/java/com/eu/habbo/habbohotel/catalog/CatalogManager.java index b274b1be..886e4928 100644 --- a/src/main/java/com/eu/habbo/habbohotel/catalog/CatalogManager.java +++ b/src/main/java/com/eu/habbo/habbohotel/catalog/CatalogManager.java @@ -902,7 +902,9 @@ public class CatalogManager { boolean badgeFound = false; for (int i = 0; i < amount; i++) { - habbo.getHabboStats().addLtdLog(item.getId(), Emulator.getIntUnixTimestamp()); + if(item.isLimited()) { + habbo.getHabboStats().addLtdLog(item.getId(), Emulator.getIntUnixTimestamp()); + } for (Item baseItem : item.getBaseItems()) { for (int k = 0; k < item.getItemAmount(baseItem.getId()); k++) { diff --git a/src/main/java/com/eu/habbo/habbohotel/commands/CommandHandler.java b/src/main/java/com/eu/habbo/habbohotel/commands/CommandHandler.java index 64dd09d8..b2f98f3a 100644 --- a/src/main/java/com/eu/habbo/habbohotel/commands/CommandHandler.java +++ b/src/main/java/com/eu/habbo/habbohotel/commands/CommandHandler.java @@ -62,7 +62,7 @@ public class CommandHandler { public static boolean handleCommand(GameClient gameClient, String commandLine) { - if (gameClient != null) { + if (gameClient != null && commandLine != null) { if (commandLine.startsWith(":")) { commandLine = commandLine.replaceFirst(":", ""); diff --git a/src/main/java/com/eu/habbo/habbohotel/items/interactions/InteractionWired.java b/src/main/java/com/eu/habbo/habbohotel/items/interactions/InteractionWired.java index 166768cb..f2541e11 100644 --- a/src/main/java/com/eu/habbo/habbohotel/items/interactions/InteractionWired.java +++ b/src/main/java/com/eu/habbo/habbohotel/items/interactions/InteractionWired.java @@ -16,11 +16,12 @@ import java.sql.Connection; import java.sql.PreparedStatement; import java.sql.ResultSet; import java.sql.SQLException; +import java.util.HashMap; public abstract class InteractionWired extends InteractionDefault { private static final Logger LOGGER = LoggerFactory.getLogger(InteractionWired.class); private long cooldown; - private TLongLongHashMap userExecutionCache = new TLongLongHashMap(3); + private final HashMap userExecutionCache = new HashMap<>(); InteractionWired(ResultSet set, Item baseItem) throws SQLException { super(set, baseItem); @@ -76,8 +77,10 @@ public abstract class InteractionWired extends InteractionDefault { } public void activateBox(Room room, RoomUnit roomUnit, long millis) { - this.setExtradata(this.getExtradata().equals("1") ? "0" : "1"); - room.sendComposer(new ItemStateComposer(this).compose()); + if(!room.isHideWired()) { + this.setExtradata(this.getExtradata().equals("1") ? "0" : "1"); + room.sendComposer(new ItemStateComposer(this).compose()); + } if (roomUnit != null) { this.addUserExecutionCache(roomUnit.getId(), millis); } @@ -112,7 +115,7 @@ public abstract class InteractionWired extends InteractionDefault { } else { if (this.userExecutionCache.containsKey((long)roomUnitId)) { long lastTimestamp = this.userExecutionCache.get((long)roomUnitId); - if (timestamp - lastTimestamp < 100L) { + if (timestamp - lastTimestamp < Math.max(100L, this.requiredCooldown())) { return false; } } diff --git a/src/main/java/com/eu/habbo/habbohotel/items/interactions/wired/triggers/WiredTriggerRepeater.java b/src/main/java/com/eu/habbo/habbohotel/items/interactions/wired/triggers/WiredTriggerRepeater.java index f43ffac0..d7e6af03 100644 --- a/src/main/java/com/eu/habbo/habbohotel/items/interactions/wired/triggers/WiredTriggerRepeater.java +++ b/src/main/java/com/eu/habbo/habbohotel/items/interactions/wired/triggers/WiredTriggerRepeater.java @@ -125,10 +125,16 @@ public class WiredTriggerRepeater extends InteractionWiredTrigger implements ICy @Override public void cycle(Room room) { this.counter += 500; - if (this.counter >= this.repeatTime) { + long currentMillis = System.currentTimeMillis(); + String Key = Double.toString(this.getX()) + Double.toString(this.getY()); + + room.repeatersLastTick.putIfAbsent(Key, currentMillis); + + if (this.counter >= this.repeatTime && room.repeatersLastTick.get(Key) < currentMillis - 450) { this.counter = 0; if (this.getRoomId() != 0) { if (room.isLoaded()) { + room.repeatersLastTick.put(Key, currentMillis); WiredHandler.handle(this, null, room, new Object[]{this}); } } diff --git a/src/main/java/com/eu/habbo/habbohotel/items/interactions/wired/triggers/WiredTriggerRepeaterLong.java b/src/main/java/com/eu/habbo/habbohotel/items/interactions/wired/triggers/WiredTriggerRepeaterLong.java index 536aca86..0723ba1f 100644 --- a/src/main/java/com/eu/habbo/habbohotel/items/interactions/wired/triggers/WiredTriggerRepeaterLong.java +++ b/src/main/java/com/eu/habbo/habbohotel/items/interactions/wired/triggers/WiredTriggerRepeaterLong.java @@ -119,10 +119,16 @@ public class WiredTriggerRepeaterLong extends InteractionWiredTrigger implements @Override public void cycle(Room room) { this.counter += 500; - if (this.counter >= this.repeatTime) { + long currentMillis = System.currentTimeMillis(); + String Key = Double.toString(this.getX()) + Double.toString(this.getY()); + + room.repeatersLastTick.putIfAbsent(Key, currentMillis); + + if (this.counter >= this.repeatTime && room.repeatersLastTick.get(Key) < currentMillis - 4950) { this.counter = 0; if (this.getRoomId() != 0) { if (room.isLoaded()) { + room.repeatersLastTick.put(Key, currentMillis); WiredHandler.handle(this, null, room, new Object[]{this}); } } diff --git a/src/main/java/com/eu/habbo/habbohotel/modtool/WordFilter.java b/src/main/java/com/eu/habbo/habbohotel/modtool/WordFilter.java index 791d12d5..68168d61 100644 --- a/src/main/java/com/eu/habbo/habbohotel/modtool/WordFilter.java +++ b/src/main/java/com/eu/habbo/habbohotel/modtool/WordFilter.java @@ -194,6 +194,10 @@ public class WordFilter { } } + public THashSet getWords() { + return new THashSet<>(this.words); + } + public void addWord(WordFilterWord word) { this.words.add(word); } diff --git a/src/main/java/com/eu/habbo/habbohotel/rooms/Room.java b/src/main/java/com/eu/habbo/habbohotel/rooms/Room.java index 119df291..e98dd691 100644 --- a/src/main/java/com/eu/habbo/habbohotel/rooms/Room.java +++ b/src/main/java/com/eu/habbo/habbohotel/rooms/Room.java @@ -213,6 +213,7 @@ public class Room implements Comparable, ISerialize, Runnable { private TraxManager traxManager; private boolean cycleOdd; private long cycleTimestamp; + public Map repeatersLastTick = new HashMap<>(); public Room(ResultSet set) throws SQLException { this.id = set.getInt("id"); diff --git a/src/main/java/com/eu/habbo/habbohotel/rooms/RoomManager.java b/src/main/java/com/eu/habbo/habbohotel/rooms/RoomManager.java index ab507719..3bf26bcc 100644 --- a/src/main/java/com/eu/habbo/habbohotel/rooms/RoomManager.java +++ b/src/main/java/com/eu/habbo/habbohotel/rooms/RoomManager.java @@ -294,6 +294,10 @@ public class RoomManager { public Room loadRoom(int id, boolean loadData) { Room room = null; + if(id == 0) { + return null; + } + if (this.activeRooms.containsKey(id)) { room = this.activeRooms.get(id); @@ -414,7 +418,7 @@ public class RoomManager { public RoomLayout loadLayout(String name, Room room) { RoomLayout layout = null; - try (Connection connection = Emulator.getDatabase().getDataSource().getConnection(); PreparedStatement statement = connection.prepareStatement("SELECT * FROM room_models WHERE name LIKE ? LIMIT 1")) { + try (Connection connection = Emulator.getDatabase().getDataSource().getConnection(); PreparedStatement statement = connection.prepareStatement("SELECT * FROM room_models WHERE name = ? LIMIT 1")) { statement.setString(1, name); try (ResultSet set = statement.executeQuery()) { if (set.next()) { diff --git a/src/main/java/com/eu/habbo/habbohotel/users/Habbo.java b/src/main/java/com/eu/habbo/habbohotel/users/Habbo.java index 6e6029f2..4dd34962 100644 --- a/src/main/java/com/eu/habbo/habbohotel/users/Habbo.java +++ b/src/main/java/com/eu/habbo/habbohotel/users/Habbo.java @@ -448,18 +448,23 @@ public class Habbo implements Runnable { } public void clearCaches() { - int timestamp = Emulator.getIntUnixTimestamp(); - THashMap> newLog = new THashMap<>(); - for (Map.Entry> ltdLog : this.habboStats.ltdPurchaseLog.entrySet()) { - for (Integer time : ltdLog.getValue()) { - if (time > timestamp) { - if (!newLog.containsKey(ltdLog.getKey())) { - newLog.put(ltdLog.getKey(), new ArrayList<>()); - } + int currentTimestamp = Emulator.getIntUnixTimestamp(); + int twentyFourHoursInSeconds = 24 * 60 * 60; // 24 hours in seconds - newLog.get(ltdLog.getKey()).add(time); + THashMap> newLog = new THashMap<>(); + + for (Map.Entry> ltdLog : this.habboStats.ltdPurchaseLog.entrySet()) { + List filteredTimestamps = new ArrayList<>(); + + for (Integer time : ltdLog.getValue()) { + if (currentTimestamp - time <= twentyFourHoursInSeconds) { + filteredTimestamps.add(time); } } + + if (!filteredTimestamps.isEmpty()) { + newLog.put(ltdLog.getKey(), filteredTimestamps); + } } this.habboStats.ltdPurchaseLog = newLog; diff --git a/src/main/java/com/eu/habbo/habbohotel/users/HabboStats.java b/src/main/java/com/eu/habbo/habbohotel/users/HabboStats.java index 462af849..29ef2a2f 100644 --- a/src/main/java/com/eu/habbo/habbohotel/users/HabboStats.java +++ b/src/main/java/com/eu/habbo/habbohotel/users/HabboStats.java @@ -102,7 +102,7 @@ public class HabboStats implements Runnable { public THashSet subscriptions; private HabboStats(ResultSet set, HabboInfo habboInfo) throws SQLException { - this.cache = new THashMap<>(0); + this.cache = new THashMap<>(1000); this.achievementProgress = new THashMap<>(0); this.achievementCache = new THashMap<>(0); this.recentPurchases = new THashMap<>(0); diff --git a/src/main/java/com/eu/habbo/habbohotel/wired/WiredHandler.java b/src/main/java/com/eu/habbo/habbohotel/wired/WiredHandler.java index 1d2b20fc..955cf264 100644 --- a/src/main/java/com/eu/habbo/habbohotel/wired/WiredHandler.java +++ b/src/main/java/com/eu/habbo/habbohotel/wired/WiredHandler.java @@ -234,7 +234,7 @@ public class WiredHandler { executed = true; if (!effect.requiresTriggeringUser() || (roomUnit != null && effect.requiresTriggeringUser())) { Emulator.getThreading().run(() -> { - if (room.isLoaded()) { + if (room.isLoaded() && room.getHabbos().size() > 0) { try { if (!effect.execute(roomUnit, room, stuff)) return; effect.setCooldown(millis); diff --git a/src/main/java/com/eu/habbo/habbohotel/wired/highscores/WiredHighscoreManager.java b/src/main/java/com/eu/habbo/habbohotel/wired/highscores/WiredHighscoreManager.java index e7cf9cef..d1769ac0 100644 --- a/src/main/java/com/eu/habbo/habbohotel/wired/highscores/WiredHighscoreManager.java +++ b/src/main/java/com/eu/habbo/habbohotel/wired/highscores/WiredHighscoreManager.java @@ -154,6 +154,18 @@ public class WiredHighscoreManager { return false; } + public HashMap> getData() { + return this.data; + } + + public List getEntriesForItemId(int itemId) { + return this.data.get(itemId); + } + + public void setEntriesForItemId(int itemId, List entries) { + this.data.put(itemId, entries); + } + private long getTodayStartTimestamp() { return LocalDateTime.now().with(LocalTime.MIDNIGHT).atZone(zoneId).toEpochSecond(); } diff --git a/src/main/java/com/eu/habbo/messages/outgoing/rooms/UpdateStackHeightComposer.java b/src/main/java/com/eu/habbo/messages/outgoing/rooms/UpdateStackHeightComposer.java index a6d5d643..9da42a67 100644 --- a/src/main/java/com/eu/habbo/messages/outgoing/rooms/UpdateStackHeightComposer.java +++ b/src/main/java/com/eu/habbo/messages/outgoing/rooms/UpdateStackHeightComposer.java @@ -8,6 +8,8 @@ import com.eu.habbo.messages.outgoing.MessageComposer; import com.eu.habbo.messages.outgoing.Outgoing; import gnu.trove.set.hash.THashSet; +import java.util.Objects; + public class UpdateStackHeightComposer extends MessageComposer { private int x; private int y; @@ -34,6 +36,7 @@ public class UpdateStackHeightComposer extends MessageComposer { //TODO: maybe do this another way? doesn't seem to be very clean but gets the job done this.response.init(Outgoing.UpdateStackHeightComposer); if (this.updateTiles != null) { + this.updateTiles.removeIf(Objects::isNull); // prevent overflow. Byte max value is 127 if(this.updateTiles.size() > 127) { RoomTile[] tiles = this.updateTiles.toArray(new RoomTile[updateTiles.size()]);