You've already forked Arcturus-Morningstar-Extended
mirror of
https://github.com/duckietm/Arcturus-Morningstar-Extended.git
synced 2026-06-20 15:36:17 +00:00
Added Plugins
This commit is contained in:
@@ -0,0 +1,2 @@
|
||||
# Auto detect text files and perform LF normalization
|
||||
* text=auto
|
||||
@@ -0,0 +1,19 @@
|
||||
target/
|
||||
pom.xml.tag
|
||||
pom.xml.releaseBackup
|
||||
pom.xml.versionsBackup
|
||||
pom.xml.next
|
||||
release.properties
|
||||
dependency-reduced-pom.xml
|
||||
buildNumber.properties
|
||||
.mvn/timing.properties
|
||||
# https://github.com/takari/maven-wrapper#usage-without-binary-jar
|
||||
.mvn/wrapper/maven-wrapper.jar
|
||||
|
||||
# Eclipse m2e generated files
|
||||
# Eclipse Core
|
||||
.project
|
||||
# JDT-specific (Eclipse Java Development Tools)
|
||||
.classpath
|
||||
|
||||
.idea
|
||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -0,0 +1,21 @@
|
||||
MIT License
|
||||
|
||||
Copyright (c) 2023 ThisAccountHasBeenSuspended, EntenKoeniq, habbo.sx
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
@@ -0,0 +1,64 @@
|
||||
# 📷 Camera
|
||||
|
||||
**New features compared to Apollyon**
|
||||
- [x] Small and more efficient than Apollyon.
|
||||
- [x] `*_small.png` are really small (original / 2) and not just copied.
|
||||
- [x] Creates a folder structure if it doesn't exist.
|
||||
- [x] Report failures to Habbo.
|
||||
- [x] Added a cooldown time for taking photos to prevent your hard drive from filling up.
|
||||
- [x] Prevent exploits on thumbnails, not just photos.
|
||||
- [x] No more FTP (no one used that).
|
||||
|
||||
[Download the latest compiled version here!](https://git.krews.org/duckietm/habbocamera/-/blob/main/Compiled/Camera-1.6.jar)
|
||||
|
||||
## Informations
|
||||
All missing settings in the database will be created with this plugin after the first launch of your emulator.
|
||||
### emulator_settings
|
||||
- `camera.url`
|
||||
- - The URL from which you can access the image (default: http://localhost/camera/)
|
||||
- `imager.location.output.camera`
|
||||
- - The location where to save the photo (default: C:/inetpub/wwwroot/public/camera/)
|
||||
- `imager.location.output.thumbnail`
|
||||
- - The location to save the thumbnail (default: C:/inetpub/wwwroot/public/camera/thumbnails/)
|
||||
- `camera.price.points.publish`
|
||||
- - The price of points for publishing this photo (default: 1)
|
||||
- `camera.price.points.publish.type`
|
||||
- - The type of points to publish (default: 5 = diamonds)
|
||||
- `camera.publish.delay`
|
||||
- - The time, in seconds, how long the user should wait to post a new photo (default: 180)
|
||||
- `camera.price.credits`
|
||||
- - The credits required to purchase this photo (default: 2)
|
||||
- `camera.price.points`
|
||||
- - The price of points to purchase this photo (default: 0 = no points required)
|
||||
- `camera.price.points.type`
|
||||
- - The type of points to buy this photo (default: 5 = diamonds)
|
||||
- `camera.render.delay`
|
||||
- - The time, in seconds, how long the user should wait to take a new photo (default: 5)
|
||||
### emulator_texts
|
||||
- `camera.permission`
|
||||
- - default: "You don't have permission to use the camera!"
|
||||
- `camera.wait`
|
||||
- - default: "Please wait %seconds% seconds before making another picture."
|
||||
- `camera.error.creation`
|
||||
- - default: "Failed to create your picture. \*sadpanda\*"
|
||||
|
||||
Since this plugin doesn't use FTP like “Apollyon”, you can delete these values in your database under `emulator_settings` if necessary.
|
||||
|
||||
## Comparison
|
||||
Apollyon doesn't show you any errors like you don't have enough currency, this plugin doesn't have that bug as shown in the pictures.
|
||||
|
||||
### Apollyon
|
||||

|
||||

|
||||
|
||||
### Camera
|
||||

|
||||

|
||||
|
||||
# Credits
|
||||
|
||||
- EntenKoeniq for releaseing the fixes and rewritten the plugin. (This camera plugin was written for https://habbo.sx/ and is now available to the community for free.)
|
||||
- John
|
||||
- Beny (Packet Hijacking)
|
||||
- Ovflowd (Original Implimentation)
|
||||
- Alejandro (Error Handling Help)
|
||||
@@ -0,0 +1,37 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project xmlns="http://maven.apache.org/POM/4.0.0"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
<groupId>com.eu.camera</groupId>
|
||||
<artifactId>Camera</artifactId>
|
||||
<version>1.6</version>
|
||||
<build>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-compiler-plugin</artifactId>
|
||||
<configuration>
|
||||
<source>11</source>
|
||||
<target>11</target>
|
||||
</configuration>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
|
||||
<properties>
|
||||
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
||||
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
|
||||
<maven.compiler.source>1.8</maven.compiler.source>
|
||||
<maven.compiler.target>1.8</maven.compiler.target>
|
||||
</properties>
|
||||
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>com.eu.habbo</groupId>
|
||||
<artifactId>Habbo</artifactId>
|
||||
<version>3.5.2</version>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
</project>
|
||||
@@ -0,0 +1,101 @@
|
||||
package com.eu.camera;
|
||||
|
||||
import com.eu.camera.handlers.PublishPhotoEvent;
|
||||
import com.eu.camera.handlers.PurchasePhotoEvent;
|
||||
import com.eu.camera.handlers.RenderRoomEvent;
|
||||
import com.eu.camera.handlers.RenderRoomThumbnailEvent;
|
||||
|
||||
import com.eu.habbo.Emulator;
|
||||
import com.eu.habbo.habbohotel.users.Habbo;
|
||||
import com.eu.habbo.messages.PacketManager;
|
||||
import com.eu.habbo.messages.incoming.Incoming;
|
||||
import com.eu.habbo.messages.incoming.MessageHandler;
|
||||
import com.eu.habbo.plugin.EventHandler;
|
||||
import com.eu.habbo.plugin.EventListener;
|
||||
import com.eu.habbo.plugin.HabboPlugin;
|
||||
import com.eu.habbo.plugin.events.emulator.EmulatorLoadedEvent;
|
||||
|
||||
import gnu.trove.map.hash.THashMap;
|
||||
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import java.io.File;
|
||||
import java.lang.reflect.Field;
|
||||
|
||||
public class Main extends HabboPlugin implements EventListener {
|
||||
private static final Logger LOGGER = LoggerFactory.getLogger(Emulator.class);
|
||||
|
||||
@Override
|
||||
public void onEnable() throws Exception {
|
||||
Emulator.getPluginManager().registerEvents(this, this);
|
||||
|
||||
if (Emulator.isReady && !Emulator.isShuttingDown) {
|
||||
this.onEmulatorLoadedEvent(null);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDisable() throws Exception {
|
||||
PacketManager packetManager = Emulator.getGameServer().getPacketManager();
|
||||
Field incomingField = PacketManager.class.getDeclaredField("incoming");
|
||||
incomingField.setAccessible(true);
|
||||
@SuppressWarnings("unchecked")
|
||||
THashMap<Integer, Class<? extends MessageHandler>> incoming = (THashMap<Integer, Class<? extends MessageHandler>>)incomingField.get(packetManager);
|
||||
|
||||
// Removes the custom handlers for these packets.
|
||||
incoming.remove(Incoming.CameraPublishToWebEvent, PublishPhotoEvent.class);
|
||||
incoming.remove(Incoming.CameraPurchaseEvent, PurchasePhotoEvent.class);
|
||||
incoming.remove(Incoming.CameraRoomPictureEvent, RenderRoomEvent.class);
|
||||
incoming.remove(Incoming.CameraRoomThumbnailEvent, RenderRoomThumbnailEvent.class);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasPermission(Habbo habbo, String string) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onEmulatorLoadedEvent(EmulatorLoadedEvent event) throws NoSuchFieldException, IllegalArgumentException, IllegalAccessException, Exception {
|
||||
// Adds missing SQLs if they are not found.
|
||||
Emulator.getConfig().register("camera.url", "http://localhost/camera/");
|
||||
Emulator.getConfig().register("imager.location.output.camera", "C:/inetpub/wwwroot/public/camera/");
|
||||
Emulator.getConfig().register("imager.location.output.thumbnail", "C:/inetpub/wwwroot/camera/thumbnails/");
|
||||
Emulator.getConfig().register("camera.price.points.publish", "1");
|
||||
Emulator.getConfig().register("camera.price.points.publish.type", "5");
|
||||
Emulator.getConfig().register("camera.publish.delay", "180");
|
||||
Emulator.getConfig().register("camera.price.credits", "2");
|
||||
Emulator.getConfig().register("camera.price.points", "0");
|
||||
Emulator.getConfig().register("camera.price.points.type", "5");
|
||||
Emulator.getConfig().register("camera.render.delay", "5");
|
||||
Emulator.getTexts().register("camera.permission", "You don't have permission to use the camera!");
|
||||
Emulator.getTexts().register("camera.wait", "Please wait %seconds% seconds before making another picture.");
|
||||
Emulator.getTexts().register("camera.error.creation", "Failed to create your picture. *sadpanda*");
|
||||
|
||||
PacketManager packetManager = Emulator.getGameServer().getPacketManager();
|
||||
Field incomingField = PacketManager.class.getDeclaredField("incoming");
|
||||
incomingField.setAccessible(true);
|
||||
@SuppressWarnings("unchecked")
|
||||
THashMap<Integer, Class<? extends MessageHandler>> incoming = (THashMap<Integer, Class<? extends MessageHandler>>)incomingField.get(packetManager);
|
||||
|
||||
// Removes the current handlers for these packets.
|
||||
incoming.remove(Incoming.CameraPublishToWebEvent);
|
||||
incoming.remove(Incoming.CameraPurchaseEvent);
|
||||
incoming.remove(Incoming.CameraRoomPictureEvent);
|
||||
incoming.remove(Incoming.CameraRoomThumbnailEvent);
|
||||
|
||||
// Adds the new handlers for these packets.
|
||||
packetManager.registerHandler(Incoming.CameraPublishToWebEvent, PublishPhotoEvent.class);
|
||||
packetManager.registerHandler(Incoming.CameraPurchaseEvent, PurchasePhotoEvent.class);
|
||||
packetManager.registerHandler(Incoming.CameraRoomPictureEvent, RenderRoomEvent.class);
|
||||
packetManager.registerHandler(Incoming.CameraRoomThumbnailEvent, RenderRoomThumbnailEvent.class);
|
||||
|
||||
// Create the output directories if they don't exist.
|
||||
File outputDir = new File(Emulator.getConfig().getValue("imager.location.output.thumbnail"));
|
||||
if (!outputDir.exists()) {
|
||||
outputDir.mkdirs();
|
||||
}
|
||||
|
||||
LOGGER.info("[Camera] Plugin has loaded!");
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,71 @@
|
||||
package com.eu.camera.handlers;
|
||||
|
||||
import com.eu.habbo.Emulator;
|
||||
import com.eu.habbo.habbohotel.users.Habbo;
|
||||
import com.eu.habbo.habbohotel.users.HabboInfo;
|
||||
import com.eu.habbo.messages.incoming.MessageHandler;
|
||||
import com.eu.habbo.messages.outgoing.camera.CameraPublishWaitMessageComposer;
|
||||
import com.eu.habbo.messages.outgoing.catalog.NotEnoughPointsTypeComposer;
|
||||
import com.eu.habbo.plugin.events.users.UserPublishPictureEvent;
|
||||
|
||||
import java.sql.Connection;
|
||||
import java.sql.PreparedStatement;
|
||||
import java.sql.SQLException;
|
||||
|
||||
public class PublishPhotoEvent extends MessageHandler {
|
||||
public static final int CAMERA_PUBLISH_POINTS = Emulator.getConfig().getInt("camera.price.points.publish", 1);
|
||||
public static final int CAMERA_PUBLISH_POINTS_TYPE = Emulator.getConfig().getInt("camera.price.points.publish.type", 5);
|
||||
public static final int CAMERA_PUBLISH_DELAY = Emulator.getConfig().getInt("camera.publish.delay", 180);
|
||||
|
||||
@Override
|
||||
public void handle() {
|
||||
Habbo habbo = this.client.getHabbo();
|
||||
HabboInfo habboInfo = habbo.getHabboInfo();
|
||||
|
||||
int points = habboInfo.getCurrencyAmount(CAMERA_PUBLISH_POINTS_TYPE);
|
||||
|
||||
if (points < CAMERA_PUBLISH_POINTS) {
|
||||
String currencyName = Emulator.getTexts().getValue("seasonal.name." + Integer.toString(CAMERA_PUBLISH_POINTS_TYPE), "currency");
|
||||
String alertMessage = "You don't have enough " + currencyName + "!";
|
||||
habbo.alert(alertMessage);
|
||||
this.client.sendResponse(new NotEnoughPointsTypeComposer(false, true, CAMERA_PUBLISH_POINTS_TYPE));
|
||||
return;
|
||||
}
|
||||
|
||||
int photoTimestamp = habboInfo.getPhotoTimestamp();
|
||||
String photoJSON = habboInfo.getPhotoJSON();
|
||||
|
||||
if (photoTimestamp == 0 || photoJSON.isEmpty() || !photoJSON.contains(Integer.toString(photoTimestamp))) {
|
||||
return;
|
||||
}
|
||||
|
||||
int currentTimestamp = Emulator.getIntUnixTimestamp();
|
||||
int timeSinceLastPublish = currentTimestamp - habboInfo.getWebPublishTimestamp();
|
||||
|
||||
if (timeSinceLastPublish < CAMERA_PUBLISH_DELAY) {
|
||||
int wait = CAMERA_PUBLISH_DELAY - timeSinceLastPublish;
|
||||
this.client.sendResponse(new CameraPublishWaitMessageComposer(false, wait, habboInfo.getPhotoURL()));
|
||||
} else {
|
||||
UserPublishPictureEvent publishPictureEvent = new UserPublishPictureEvent(habbo, habboInfo.getPhotoURL(), currentTimestamp, habboInfo.getPhotoRoomId());
|
||||
|
||||
if (!Emulator.getPluginManager().fireEvent(publishPictureEvent).isCancelled()) {
|
||||
try (Connection connection = Emulator.getDatabase().getDataSource().getConnection();
|
||||
PreparedStatement statement = connection.prepareStatement("INSERT INTO camera_web (user_id, room_id, timestamp, url) VALUES (?, ?, ?, ?)")) {
|
||||
statement.setInt(1, habboInfo.getId());
|
||||
statement.setInt(2, publishPictureEvent.roomId);
|
||||
statement.setInt(3, publishPictureEvent.timestamp);
|
||||
statement.setString(4, publishPictureEvent.URL);
|
||||
statement.execute();
|
||||
|
||||
habboInfo.setWebPublishTimestamp(currentTimestamp);
|
||||
|
||||
habbo.givePoints(CAMERA_PUBLISH_POINTS_TYPE, -CAMERA_PUBLISH_POINTS);
|
||||
} catch (SQLException throwable) {
|
||||
throwable.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
this.client.sendResponse(new CameraPublishWaitMessageComposer(true, 0, ""));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,87 @@
|
||||
package com.eu.camera.handlers;
|
||||
|
||||
import com.eu.habbo.Emulator;
|
||||
import com.eu.habbo.habbohotel.achievements.AchievementManager;
|
||||
import com.eu.habbo.habbohotel.items.Item;
|
||||
import com.eu.habbo.habbohotel.users.Habbo;
|
||||
import com.eu.habbo.habbohotel.users.HabboInfo;
|
||||
import com.eu.habbo.habbohotel.users.HabboItem;
|
||||
import com.eu.habbo.messages.incoming.MessageHandler;
|
||||
import com.eu.habbo.messages.outgoing.camera.CameraPurchaseSuccesfullComposer;
|
||||
import com.eu.habbo.messages.outgoing.catalog.NotEnoughPointsTypeComposer;
|
||||
import com.eu.habbo.messages.outgoing.inventory.AddHabboItemComposer;
|
||||
import com.eu.habbo.messages.outgoing.inventory.InventoryRefreshComposer;
|
||||
import com.eu.habbo.plugin.events.users.UserPurchasePictureEvent;
|
||||
|
||||
public class PurchasePhotoEvent extends MessageHandler {
|
||||
public static final int CAMERA_PURCHASE_CREDITS = Emulator.getConfig().getInt("camera.price.credits", 2);
|
||||
public static final int CAMERA_PURCHASE_POINTS = Emulator.getConfig().getInt("camera.price.points", 0);
|
||||
public static final int CAMERA_PURCHASE_POINTS_TYPE = Emulator.getConfig().getInt("camera.price.points.type", 5);
|
||||
public static final int CAMERA_ITEM_ID = Emulator.getConfig().getInt("camera.item_id");
|
||||
public static final String EXTERNAL_IMAGE_INTERACTION = "external_image";
|
||||
|
||||
@Override
|
||||
public void handle() {
|
||||
Habbo habbo = this.client.getHabbo();
|
||||
HabboInfo habboInfo = habbo.getHabboInfo();
|
||||
|
||||
if (habboInfo.getCredits() < CAMERA_PURCHASE_CREDITS) {
|
||||
handleInsufficientCredits(habbo);
|
||||
return;
|
||||
}
|
||||
|
||||
if (habboInfo.getCurrencyAmount(CAMERA_PURCHASE_POINTS_TYPE) < CAMERA_PURCHASE_POINTS) {
|
||||
handleInsufficientPoints(habbo);
|
||||
return;
|
||||
}
|
||||
|
||||
if (!isValidPhoto(habboInfo)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (Emulator.getPluginManager().fireEvent(new UserPurchasePictureEvent(habbo, habboInfo.getPhotoURL(), habboInfo.getCurrentRoom().getId(), habboInfo.getPhotoTimestamp())).isCancelled()) {
|
||||
return;
|
||||
}
|
||||
|
||||
Item item = Emulator.getGameEnvironment().getItemManager().getItem(CAMERA_ITEM_ID);
|
||||
if (item == null || !item.getInteractionType().getName().equals(EXTERNAL_IMAGE_INTERACTION)) {
|
||||
return;
|
||||
}
|
||||
|
||||
handlePurchasedPhoto(habbo, habboInfo, item);
|
||||
}
|
||||
|
||||
private void handleInsufficientCredits(Habbo habbo) {
|
||||
habbo.alert("You don't have enough credits!");
|
||||
this.client.sendResponse(new NotEnoughPointsTypeComposer(true, false, 0));
|
||||
}
|
||||
|
||||
private void handleInsufficientPoints(Habbo habbo) {
|
||||
String alertMessage = "You don't have enough " + Emulator.getTexts().getValue("seasonal.name." + Integer.toString(CAMERA_PURCHASE_POINTS_TYPE), "currency") + "!";
|
||||
habbo.alert(alertMessage);
|
||||
this.client.sendResponse(new NotEnoughPointsTypeComposer(false, true, CAMERA_PURCHASE_POINTS_TYPE));
|
||||
}
|
||||
|
||||
private boolean isValidPhoto(HabboInfo habboInfo) {
|
||||
return habboInfo.getPhotoTimestamp() != 0 && !habboInfo.getPhotoJSON().isEmpty() && habboInfo.getPhotoJSON().contains(Integer.toString(habboInfo.getPhotoTimestamp()));
|
||||
}
|
||||
|
||||
private void handlePurchasedPhoto(Habbo habbo, HabboInfo habboInfo, Item item) {
|
||||
HabboItem photoItem = Emulator.getGameEnvironment().getItemManager().createItem(habboInfo.getId(), item, 0, 0, habboInfo.getPhotoJSON());
|
||||
|
||||
if (photoItem != null) {
|
||||
photoItem.setExtradata(photoItem.getExtradata().replace("%id%", Integer.toString(photoItem.getId())));
|
||||
photoItem.needsUpdate(true);
|
||||
|
||||
habbo.getInventory().getItemsComponent().addItem(photoItem);
|
||||
|
||||
this.client.sendResponse(new CameraPurchaseSuccesfullComposer());
|
||||
this.client.sendResponse(new AddHabboItemComposer(photoItem));
|
||||
this.client.sendResponse(new InventoryRefreshComposer());
|
||||
|
||||
habbo.giveCredits(-CAMERA_PURCHASE_CREDITS);
|
||||
habbo.givePoints(CAMERA_PURCHASE_POINTS_TYPE, -CAMERA_PURCHASE_POINTS);
|
||||
AchievementManager.progressAchievement(habbo, Emulator.getGameEnvironment().getAchievementManager().getAchievement("CameraPhotoCount"));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,136 @@
|
||||
package com.eu.camera.handlers;
|
||||
|
||||
import com.eu.habbo.Emulator;
|
||||
import com.eu.habbo.messages.incoming.MessageHandler;
|
||||
import com.eu.habbo.habbohotel.rooms.Room;
|
||||
import com.eu.habbo.habbohotel.users.Habbo;
|
||||
import com.eu.habbo.habbohotel.users.HabboInfo;
|
||||
import com.eu.habbo.habbohotel.users.HabboStats;
|
||||
import com.eu.habbo.messages.outgoing.camera.CameraURLComposer;
|
||||
import io.netty.buffer.ByteBuf;
|
||||
import io.netty.buffer.ByteBufInputStream;
|
||||
import io.netty.buffer.ByteBufUtil;
|
||||
|
||||
import javax.imageio.ImageIO;
|
||||
import java.awt.Graphics2D;
|
||||
import java.awt.Image;
|
||||
import java.awt.image.BufferedImage;
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
|
||||
public class RenderRoomEvent extends MessageHandler {
|
||||
public static final int CAMERA_RENDER_DELAY = Emulator.getConfig().getInt("camera.render.delay", 5);
|
||||
|
||||
private ByteBuf image = null;
|
||||
|
||||
@Override
|
||||
public void handle() {
|
||||
try {
|
||||
make();
|
||||
} finally {
|
||||
if (this.image != null) {
|
||||
this.image.release();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void make() {
|
||||
Habbo habbo = this.client.getHabbo();
|
||||
if (!habbo.hasPermission("acc_camera")) {
|
||||
habbo.alert(Emulator.getTexts().getValue("camera.permission"));
|
||||
return;
|
||||
}
|
||||
|
||||
HabboInfo habboInfo = habbo.getHabboInfo();
|
||||
HabboStats habboStats = habbo.getHabboStats();
|
||||
|
||||
int timestamp = Emulator.getIntUnixTimestamp();
|
||||
|
||||
if (habboStats.cache.containsKey("camera_render_cooldown")) {
|
||||
int cameraTimestamp = (int) habboStats.cache.get("camera_render_cooldown");
|
||||
if (timestamp - cameraTimestamp < CAMERA_RENDER_DELAY) {
|
||||
String alertMessage = Emulator.getTexts().getValue("camera.wait")
|
||||
.replace("%seconds%", Integer.toString(timestamp - cameraTimestamp));
|
||||
habbo.alert(alertMessage);
|
||||
|
||||
// Show the correct last photo.
|
||||
String[] splittedPhotoURL = habboInfo.getPhotoURL().split("/");
|
||||
if (splittedPhotoURL.length > 0) {
|
||||
this.client.sendResponse(new CameraURLComposer(splittedPhotoURL[splittedPhotoURL.length - 1]));
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
}
|
||||
habboStats.cache.put("camera_render_cooldown", (Object) timestamp);
|
||||
|
||||
Room room = habboInfo.getCurrentRoom();
|
||||
if (room == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
final int count = this.packet.readInt();
|
||||
this.image = this.packet.getBuffer().readBytes(count);
|
||||
if (this.image == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Prevent possible exploits.
|
||||
byte[] imageBytes = ByteBufUtil.getBytes(this.image, 0, 4, true);
|
||||
if (imageBytes == null || imageBytes.length < 4 || !isPNG(imageBytes)) {
|
||||
return;
|
||||
}
|
||||
|
||||
BufferedImage theImage;
|
||||
try (ByteBufInputStream in = new ByteBufInputStream(this.image)) {
|
||||
theImage = ImageIO.read(in);
|
||||
} catch (IOException e) {
|
||||
handleImageProcessingError(habbo);
|
||||
return;
|
||||
}
|
||||
|
||||
String fileName = habboInfo.getId() + "_" + timestamp;
|
||||
String URL = fileName + ".png";
|
||||
String URLsmall = fileName + "_small.png";
|
||||
String base = Emulator.getConfig().getValue("camera.url");
|
||||
|
||||
String json = Emulator.getConfig().getValue("camera.extradata")
|
||||
.replace("%timestamp%", Integer.toString(timestamp))
|
||||
.replace("%room_id%", Integer.toString(room.getId()))
|
||||
.replace("%url%", base + URL);
|
||||
|
||||
habboInfo.setPhotoURL(base + URL);
|
||||
habboInfo.setPhotoTimestamp(timestamp);
|
||||
habboInfo.setPhotoRoomId(room.getId());
|
||||
habboInfo.setPhotoJSON(json);
|
||||
|
||||
File imageFile = new File(Emulator.getConfig().getValue("imager.location.output.camera") + URL);
|
||||
File smallImageFile = new File(Emulator.getConfig().getValue("imager.location.output.camera") + URLsmall);
|
||||
|
||||
try {
|
||||
ImageIO.write(theImage, "png", imageFile);
|
||||
|
||||
Image smallImage = theImage.getScaledInstance(theImage.getWidth(null) / 2, theImage.getHeight(null) / 2, Image.SCALE_SMOOTH);
|
||||
|
||||
BufferedImage bi = new BufferedImage(smallImage.getWidth(null), smallImage.getHeight(null), BufferedImage.TYPE_INT_ARGB);
|
||||
Graphics2D graphics2D = bi.createGraphics();
|
||||
graphics2D.drawImage(smallImage, 0, 0, null);
|
||||
graphics2D.dispose();
|
||||
|
||||
ImageIO.write(bi, "png", smallImageFile);
|
||||
} catch (IOException e) {
|
||||
handleImageProcessingError(habbo);
|
||||
return;
|
||||
}
|
||||
|
||||
this.client.sendResponse(new CameraURLComposer(URL));
|
||||
}
|
||||
|
||||
private boolean isPNG(byte[] bytes) {
|
||||
return bytes[0] == -119 && bytes[1] == 80 && bytes[2] == 78 && bytes[3] == 71;
|
||||
}
|
||||
|
||||
private void handleImageProcessingError(Habbo habbo) {
|
||||
habbo.alert(Emulator.getTexts().getValue("camera.error.creation"));
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,96 @@
|
||||
package com.eu.camera.handlers;
|
||||
|
||||
import com.eu.habbo.Emulator;
|
||||
import com.eu.habbo.messages.incoming.MessageHandler;
|
||||
import com.eu.habbo.habbohotel.rooms.Room;
|
||||
import com.eu.habbo.habbohotel.users.Habbo;
|
||||
import com.eu.habbo.habbohotel.users.HabboInfo;
|
||||
import com.eu.habbo.habbohotel.users.HabboStats;
|
||||
import com.eu.habbo.messages.outgoing.camera.CameraRoomThumbnailSavedComposer;
|
||||
import io.netty.buffer.ByteBuf;
|
||||
import io.netty.buffer.ByteBufInputStream;
|
||||
import io.netty.buffer.ByteBufUtil;
|
||||
import javax.imageio.ImageIO;
|
||||
import java.awt.image.BufferedImage;
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
|
||||
public class RenderRoomThumbnailEvent extends MessageHandler {
|
||||
public static final int CAMERA_RENDER_DELAY = Emulator.getConfig().getInt("camera.render.delay", 5);
|
||||
|
||||
private ByteBuf image = null;
|
||||
|
||||
@Override
|
||||
public void handle() {
|
||||
try {
|
||||
make();
|
||||
} finally {
|
||||
if (this.image != null) {
|
||||
this.image.release();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void make() {
|
||||
Habbo habbo = this.client.getHabbo();
|
||||
if (!habbo.hasPermission("acc_camera")) {
|
||||
habbo.alert(Emulator.getTexts().getValue("camera.permission"));
|
||||
return;
|
||||
}
|
||||
|
||||
HabboStats habboStats = habbo.getHabboStats();
|
||||
|
||||
int timestamp = Emulator.getIntUnixTimestamp();
|
||||
|
||||
if (habboStats.cache.containsKey("camera_render_cooldown")) {
|
||||
int cameraTimestamp = (int) habboStats.cache.get("camera_render_cooldown");
|
||||
if (timestamp - cameraTimestamp < CAMERA_RENDER_DELAY) {
|
||||
String alertMessage = Emulator.getTexts().getValue("camera.wait")
|
||||
.replace("%seconds%", Integer.toString(timestamp - cameraTimestamp));
|
||||
habbo.alert(alertMessage);
|
||||
return;
|
||||
}
|
||||
}
|
||||
habboStats.cache.put("camera_render_cooldown", (Object) timestamp);
|
||||
|
||||
HabboInfo habboInfo = habbo.getHabboInfo();
|
||||
|
||||
Room room = habboInfo.getCurrentRoom();
|
||||
if (room == null || !room.isOwner(habbo)) {
|
||||
return;
|
||||
}
|
||||
|
||||
final int count = this.packet.readInt();
|
||||
this.image = this.packet.getBuffer().readBytes(count);
|
||||
if (this.image == null || !isValidImage(this.image)) {
|
||||
return;
|
||||
}
|
||||
|
||||
BufferedImage theImage = null;
|
||||
try (ByteBufInputStream in = new ByteBufInputStream(this.image)) {
|
||||
theImage = ImageIO.read(in);
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
habbo.alert(Emulator.getTexts().getValue("camera.error.creation"));
|
||||
return;
|
||||
}
|
||||
|
||||
File imageFile = new File(Emulator.getConfig().getValue("imager.location.output.thumbnail") + room.getId() + ".png");
|
||||
|
||||
try {
|
||||
ImageIO.write(theImage, "png", imageFile);
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
habbo.alert(Emulator.getTexts().getValue("camera.error.creation"));
|
||||
return;
|
||||
}
|
||||
|
||||
this.client.sendResponse(new CameraRoomThumbnailSavedComposer());
|
||||
}
|
||||
|
||||
private boolean isValidImage(ByteBuf imageBuffer) {
|
||||
byte[] imageBytes = ByteBufUtil.getBytes(imageBuffer, 0, 4, true);
|
||||
return (imageBytes != null && imageBytes.length >= 4 &&
|
||||
imageBytes[0] == -119 && imageBytes[1] == 80 && imageBytes[2] == 78 && imageBytes[3] == 71);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
{
|
||||
"main" : "com.eu.camera.Main",
|
||||
"name" : "Camera",
|
||||
"author" : "EntenKoeniq and habbo.sx"
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user