Started implementing the Replay Center.

Expanded and generalized the ApiClient.
This commit is contained in:
Marius Metzger
2015-01-29 22:58:22 +01:00
parent 4659abc98e
commit f67e681825
9 changed files with 247 additions and 31 deletions

View File

@@ -46,6 +46,8 @@ public class ReplayMod
public static ReplaySettings replaySettings = new ReplaySettings(0, true, true, true, false, false); public static ReplaySettings replaySettings = new ReplaySettings(0, true, true, true, false, false);
public static Configuration config; public static Configuration config;
public static boolean firstMainMenu = true;
public static RecordingHandler recordingHandler; public static RecordingHandler recordingHandler;
public static int TP_DISTANCE_LIMIT = 128; public static int TP_DISTANCE_LIMIT = 128;

View File

@@ -5,21 +5,19 @@ import java.io.IOException;
import java.io.InputStream; import java.io.InputStream;
import java.net.HttpURLConnection; import java.net.HttpURLConnection;
import java.net.URL; import java.net.URL;
import java.net.URLConnection;
import java.nio.file.Files; import java.nio.file.Files;
import java.nio.file.StandardCopyOption; import java.nio.file.StandardCopyOption;
import java.util.List; import java.util.List;
import org.apache.http.HttpResponse; import org.apache.http.HttpResponse;
import org.apache.http.client.HttpClient;
import org.apache.http.client.methods.HttpPost; import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.FileEntity; import org.apache.http.entity.FileEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.DefaultHttpClient; import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.util.EntityUtils; import org.apache.http.util.EntityUtils;
import com.google.gson.Gson; import com.google.gson.Gson;
import com.google.gson.JsonElement; import com.google.gson.JsonElement;
import com.google.gson.JsonObject;
import com.google.gson.JsonParser; import com.google.gson.JsonParser;
import eu.crushedpixel.replaymod.api.client.holders.ApiError; import eu.crushedpixel.replaymod.api.client.holders.ApiError;
@@ -43,6 +41,13 @@ public class ApiClient {
return auth; return auth;
} }
public boolean logout(String auth) throws IOException, ApiException {
QueryBuilder builder = new QueryBuilder(ApiMethods.logout);
builder.put("auth", auth);
Success succ = invokeAndReturn(builder, Success.class);
return succ.isSuccess();
}
public UserFiles getUserFiles(String auth, String user) throws IOException, ApiException { public UserFiles getUserFiles(String auth, String user) throws IOException, ApiException {
QueryBuilder builder = new QueryBuilder(ApiMethods.replay_files); QueryBuilder builder = new QueryBuilder(ApiMethods.replay_files);
builder.put("auth", auth); builder.put("auth", auth);
@@ -59,30 +64,45 @@ public class ApiClient {
return info; return info;
} }
public FileInfo[] getRecentFiles() throws IOException, ApiException {
QueryBuilder builder = new QueryBuilder(ApiMethods.replay_files);
builder.put("recent", true);
FileInfo[] info = invokeAndReturn(builder, FileInfo[].class); //TODO: Test if that works
return info;
}
public FileInfo[] getBestFiles() throws IOException, ApiException {
QueryBuilder builder = new QueryBuilder(ApiMethods.replay_files);
builder.put("best", true);
FileInfo[] info = invokeAndReturn(builder, FileInfo[].class); //TODO: Test if that works
return info;
}
public void uploadFile(String auth, File file, Category category) throws IOException, ApiException { public void uploadFile(String auth, File file, Category category) throws IOException, ApiException {
QueryBuilder builder = new QueryBuilder(ApiMethods.upload_file); QueryBuilder builder = new QueryBuilder(ApiMethods.upload_file);
builder.put("auth", auth); builder.put("auth", auth);
builder.put("category", category.getId()); builder.put("category", category.getId());
String url = builder.toString(); String url = builder.toString();
HttpClient client = new DefaultHttpClient(); CloseableHttpClient client = new DefaultHttpClient();
HttpPost post = new HttpPost(url); HttpPost post = new HttpPost(url);
FileEntity entity = new FileEntity(file); FileEntity entity = new FileEntity(file);
post.setEntity(entity); post.setEntity(entity);
HttpResponse response = client.execute(post); HttpResponse response = client.execute(post);
//((InputStream)client).close(); TODO: Find working solution
if(response.getStatusLine().getStatusCode() != 200) { if(response.getStatusLine().getStatusCode() != 200) {
JsonElement element = jsonParser.parse(EntityUtils.toString(response.getEntity())); JsonElement element = jsonParser.parse(EntityUtils.toString(response.getEntity()));
try { try {
ApiError err = gson.fromJson(element, ApiError.class); ApiError err = gson.fromJson(element, ApiError.class);
if(err.getDesc() != null) { if(err.getDesc() != null) {
client.close();
throw new ApiException(err); throw new ApiException(err);
} }
} catch(Exception e) {} } catch(Exception e) {}
} }
client.close();
} }
public void downloadFile(String auth, int file, File target) throws IOException { public void downloadFile(String auth, int file, File target) throws IOException {
@@ -123,8 +143,8 @@ public class ApiClient {
} }
private <T> T invokeAndReturn(QueryBuilder builder,Class<T> classOfT) throws IOException, ApiException { private <T> T invokeAndReturn(QueryBuilder builder,Class<T> classOfT) throws IOException, ApiException {
JsonObject arr = GsonApiClient.invoke(builder); JsonElement ele = GsonApiClient.invoke(builder);
return gson.fromJson(arr, classOfT); return gson.fromJson(ele, classOfT);
} }
@SuppressWarnings("rawtypes") @SuppressWarnings("rawtypes")

View File

@@ -11,28 +11,28 @@ public class GsonApiClient {
private static final JsonParser parser = new JsonParser(); private static final JsonParser parser = new JsonParser();
public static JsonObject invoke(QueryBuilder query) throws IOException, ApiException { public static JsonElement invoke(QueryBuilder query) throws IOException, ApiException {
String apiResult = SimpleApiClient.invoke(query); String apiResult = SimpleApiClient.invoke(query);
return wrapWithJson(apiResult); return wrapWithJson(apiResult);
} }
public static JsonObject invokeJson(String url) throws IOException, ApiException { public static JsonElement invokeJson(String url) throws IOException, ApiException {
String apiResult = SimpleApiClient.invokeUrl(url); String apiResult = SimpleApiClient.invokeUrl(url);
return wrapWithJson(apiResult); return wrapWithJson(apiResult);
} }
public static JsonObject invokeJson(String apiKey, String method, Map<String,Object> paramMap) throws IOException, ApiException { public static JsonElement invokeJson(String apiKey, String method, Map<String,Object> paramMap) throws IOException, ApiException {
String apiResult = SimpleApiClient.invoke(method, paramMap); String apiResult = SimpleApiClient.invoke(method, paramMap);
return wrapWithJson(apiResult); return wrapWithJson(apiResult);
} }
public static JsonObject invokeJson(String apiKey, String method) throws IOException, ApiException { public static JsonElement invokeJson(String apiKey, String method) throws IOException, ApiException {
String apiResult = SimpleApiClient.invoke(method, null); String apiResult = SimpleApiClient.invoke(method, null);
return wrapWithJson(apiResult); return wrapWithJson(apiResult);
} }
private static JsonObject wrapWithJson(String apiResult) { private static JsonElement wrapWithJson(String apiResult) {
JsonElement element = parser.parse(apiResult); JsonElement element = parser.parse(apiResult);
return element.getAsJsonObject(); return element;
} }
} }

View File

@@ -1,10 +1,10 @@
package eu.crushedpixel.replaymod.events; package eu.crushedpixel.replaymod.events;
import java.awt.Color;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
import net.minecraft.client.Minecraft; import net.minecraft.client.Minecraft;
import net.minecraft.client.entity.EntityPlayerSP;
import net.minecraft.client.gui.GuiButton; import net.minecraft.client.gui.GuiButton;
import net.minecraft.client.gui.GuiChat; import net.minecraft.client.gui.GuiChat;
import net.minecraft.client.gui.GuiDisconnected; import net.minecraft.client.gui.GuiDisconnected;
@@ -15,11 +15,12 @@ import net.minecraft.client.gui.GuiVideoSettings;
import net.minecraft.client.gui.inventory.GuiInventory; import net.minecraft.client.gui.inventory.GuiInventory;
import net.minecraft.client.resources.I18n; import net.minecraft.client.resources.I18n;
import net.minecraft.client.settings.GameSettings.Options; import net.minecraft.client.settings.GameSettings.Options;
import net.minecraftforge.client.GuiIngameForge;
import net.minecraftforge.client.event.GuiOpenEvent; import net.minecraftforge.client.event.GuiOpenEvent;
import net.minecraftforge.client.event.GuiScreenEvent.ActionPerformedEvent; import net.minecraftforge.client.event.GuiScreenEvent.ActionPerformedEvent;
import net.minecraftforge.client.event.GuiScreenEvent.DrawScreenEvent;
import net.minecraftforge.client.event.GuiScreenEvent.InitGuiEvent; import net.minecraftforge.client.event.GuiScreenEvent.InitGuiEvent;
import net.minecraftforge.fml.common.eventhandler.SubscribeEvent; import net.minecraftforge.fml.common.eventhandler.SubscribeEvent;
import eu.crushedpixel.replaymod.ReplayMod;
import eu.crushedpixel.replaymod.gui.GuiConstants; import eu.crushedpixel.replaymod.gui.GuiConstants;
import eu.crushedpixel.replaymod.gui.GuiReplaySaving; import eu.crushedpixel.replaymod.gui.GuiReplaySaving;
import eu.crushedpixel.replaymod.gui.GuiReplaySettings; import eu.crushedpixel.replaymod.gui.GuiReplaySettings;
@@ -29,7 +30,6 @@ import eu.crushedpixel.replaymod.gui.replaymanager.GuiReplayManager;
import eu.crushedpixel.replaymod.gui.replaymanager.ResourceHelper; import eu.crushedpixel.replaymod.gui.replaymanager.ResourceHelper;
import eu.crushedpixel.replaymod.online.authentication.AuthenticationHandler; import eu.crushedpixel.replaymod.online.authentication.AuthenticationHandler;
import eu.crushedpixel.replaymod.registry.ReplayGuiRegistry; import eu.crushedpixel.replaymod.registry.ReplayGuiRegistry;
import eu.crushedpixel.replaymod.renderer.SafeEntityRenderer;
import eu.crushedpixel.replaymod.replay.ReplayHandler; import eu.crushedpixel.replaymod.replay.ReplayHandler;
public class GuiEventHandler { public class GuiEventHandler {
@@ -48,6 +48,12 @@ public class GuiEventHandler {
@SubscribeEvent @SubscribeEvent
public void onGui(GuiOpenEvent event) { public void onGui(GuiOpenEvent event) {
if(ReplayMod.firstMainMenu && event.gui instanceof GuiMainMenu) {
ReplayMod.firstMainMenu = false;
event.gui = new GuiLoginPrompt(event.gui, event.gui);
return;
}
if(!AuthenticationHandler.isAuthenticated()) return; if(!AuthenticationHandler.isAuthenticated()) return;
if(event.gui != null && GuiReplaySaving.replaySaving && !allowedGUIs.contains(event.gui.getClass())) { if(event.gui != null && GuiReplaySaving.replaySaving && !allowedGUIs.contains(event.gui.getClass())) {
event.gui = new GuiReplaySaving(event.gui); event.gui = new GuiReplaySaving(event.gui);
@@ -67,6 +73,21 @@ public class GuiEventHandler {
} }
} }
private static final Color DARK_RED = Color.decode("#DF0101");
private static final Color DARK_GREEN = Color.decode("#01DF01");
@SubscribeEvent
public void onDraw(DrawScreenEvent e) {
if(e.gui instanceof GuiMainMenu) {
e.gui.drawString(mc.fontRendererObj, "Replay Mod:", 5, 5, Color.WHITE.getRGB());
if(AuthenticationHandler.isAuthenticated()) {
e.gui.drawString(mc.fontRendererObj, "LOGGED IN", 5, 15, DARK_GREEN.getRGB());
} else {
e.gui.drawString(mc.fontRendererObj, "LOGGED OUT", 5, 15, DARK_RED.getRGB());
}
}
}
@SubscribeEvent @SubscribeEvent
public void onInit(InitGuiEvent event) { public void onInit(InitGuiEvent event) {
if(event.gui instanceof GuiIngameMenu && ReplayHandler.replayActive()) { if(event.gui instanceof GuiIngameMenu && ReplayHandler.replayActive()) {
@@ -110,7 +131,11 @@ public class GuiEventHandler {
if(event.button.id == GuiConstants.REPLAY_MANAGER_BUTTON_ID) { if(event.button.id == GuiConstants.REPLAY_MANAGER_BUTTON_ID) {
mc.displayGuiScreen(new GuiReplayManager()); mc.displayGuiScreen(new GuiReplayManager());
} else if(event.button.id == GuiConstants.REPLAY_CENTER_BUTTON_ID) { } else if(event.button.id == GuiConstants.REPLAY_CENTER_BUTTON_ID) {
mc.displayGuiScreen(new GuiLoginPrompt(event.gui, new GuiReplayCenter())); if(AuthenticationHandler.isAuthenticated()) {
mc.displayGuiScreen(new GuiReplayCenter());
} else {
mc.displayGuiScreen(new GuiLoginPrompt(event.gui, new GuiReplayCenter()));
}
} }
} else if(event.gui instanceof GuiOptions && event.button.id == GuiConstants.REPLAY_OPTIONS_BUTTON_ID) { } else if(event.gui instanceof GuiOptions && event.button.id == GuiConstants.REPLAY_OPTIONS_BUTTON_ID) {
mc.displayGuiScreen(new GuiReplaySettings(event.gui)); mc.displayGuiScreen(new GuiReplaySettings(event.gui));

View File

@@ -2,6 +2,12 @@ package eu.crushedpixel.replaymod.gui;
public class GuiConstants { public class GuiConstants {
public static final int CENTER_OVERVIEW_BUTTON = 2000;
public static final int CENTER_MY_REPLAYS_BUTTON = 2001;
public static final int CENTER_UPLOAD_BUTTON = 2002;
public static final int CENTER_BACK_BUTTON = 2003;
public static final int CENTER_LOGOUT_BUTTON = 2004;
public static final int REPLAY_OPTIONS_BUTTON_ID = 8000; public static final int REPLAY_OPTIONS_BUTTON_ID = 8000;
public static final int REPLAY_MANAGER_BUTTON_ID = 9001; public static final int REPLAY_MANAGER_BUTTON_ID = 9001;

View File

@@ -66,7 +66,7 @@ public class GuiLoginPrompt extends GuiScreen {
//Authenticate //Authenticate
textState = LOGGING_IN; textState = LOGGING_IN;
Thread loginThread = new Thread(new Runnable() { mc.addScheduledTask(new Runnable() {
@Override @Override
public void run() { public void run() {
switch(AuthenticationHandler.authenticate(username.getText(), password.getText())) { switch(AuthenticationHandler.authenticate(username.getText(), password.getText())) {
@@ -83,8 +83,6 @@ public class GuiLoginPrompt extends GuiScreen {
} }
} }
}); });
loginThread.start();
} }
} else if(button.id == GuiConstants.LOGIN_CANCEL_BUTTON) { } else if(button.id == GuiConstants.LOGIN_CANCEL_BUTTON) {
mc.displayGuiScreen(parent); mc.displayGuiScreen(parent);

View File

@@ -1,7 +1,158 @@
package eu.crushedpixel.replaymod.gui.online; package eu.crushedpixel.replaymod.gui.online;
import java.awt.Color;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import net.minecraft.client.gui.GuiButton;
import net.minecraft.client.gui.GuiMainMenu;
import net.minecraft.client.gui.GuiScreen; import net.minecraft.client.gui.GuiScreen;
import net.minecraft.client.gui.GuiYesNo;
import net.minecraft.client.gui.GuiYesNoCallback;
import net.minecraft.client.resources.I18n;
public class GuiReplayCenter extends GuiScreen { import org.lwjgl.input.Keyboard;
import scala.actors.threadpool.Arrays;
import com.mojang.realmsclient.gui.GuiCallback;
import eu.crushedpixel.replaymod.ReplayMod;
import eu.crushedpixel.replaymod.api.client.ApiException;
import eu.crushedpixel.replaymod.api.client.holders.FileInfo;
import eu.crushedpixel.replaymod.gui.GuiConstants;
import eu.crushedpixel.replaymod.online.authentication.AuthenticationHandler;
public class GuiReplayCenter extends GuiScreen implements GuiYesNoCallback {
@Override
public void initGui() {
Keyboard.enableRepeatEvents(true);
if(!AuthenticationHandler.isAuthenticated()) {
mc.displayGuiScreen(new GuiLoginPrompt(new GuiMainMenu(), this));
return;
}
//Top Button Bar
List<GuiButton> buttonBar = new ArrayList<GuiButton>();
GuiButton overviewButton = new GuiButton(GuiConstants.CENTER_OVERVIEW_BUTTON, 20, 30, "Overview");
buttonBar.add(overviewButton);
GuiButton ownReplayButton = new GuiButton(GuiConstants.CENTER_MY_REPLAYS_BUTTON, 20, 30, "My Replays");
buttonBar.add(ownReplayButton);
GuiButton uploadReplayButton = new GuiButton(GuiConstants.CENTER_UPLOAD_BUTTON, 20, 30, "Upload");
buttonBar.add(uploadReplayButton);
int i = 0;
for(GuiButton b : buttonBar) {
int w = this.width - 30;
int w2 = w/buttonBar.size();
int x = 15+(w2*i);
b.xPosition = x;
b.yPosition = 20;
b.width = w2-4;
buttonList.add(b);
i++;
}
//Bottom Button Bar (dat alliteration)
List<GuiButton> bottomBar = new ArrayList<GuiButton>();
GuiButton exitButton = new GuiButton(GuiConstants.CENTER_BACK_BUTTON, 20, 20, "Back");
bottomBar.add(exitButton);
GuiButton logoutButton = new GuiButton(GuiConstants.CENTER_LOGOUT_BUTTON, 20, 20, "Logout");
bottomBar.add(logoutButton);
i = 0;
for(GuiButton b : bottomBar) {
int w = this.width - 30;
int w2 = w/bottomBar.size();
int x = 15+(w2*i);
b.xPosition = x;
b.yPosition = height-30;
b.width = w2-4;
buttonList.add(b);
i++;
}
showOverview();
}
@Override
protected void actionPerformed(GuiButton button) throws java.io.IOException {
if(!button.enabled) return;
if(button.id == GuiConstants.CENTER_BACK_BUTTON) {
mc.displayGuiScreen(new GuiMainMenu());
return;
} else if(button.id == GuiConstants.CENTER_LOGOUT_BUTTON) {
mc.displayGuiScreen(getYesNoGui(this, LOGOUT_CALLBACK_ID));
}
}
private static final int LOGOUT_CALLBACK_ID = 1;
@Override
public void confirmClicked(boolean result, int id) {
if(id == LOGOUT_CALLBACK_ID) {
if(result) {
mc.addScheduledTask(new Runnable() {
@Override
public void run() {
AuthenticationHandler.logout();
mc.displayGuiScreen(new GuiMainMenu());
}
});
} else {
mc.displayGuiScreen(this);
}
}
}
public static GuiYesNo getYesNoGui(GuiYesNoCallback p_152129_0_, int p_152129_2_) {
String s1 = I18n.format("Do you really want to log out?", new Object[0]);
GuiYesNo guiyesno = new GuiYesNo(p_152129_0_, s1, "", "Logout", "Cancel", p_152129_2_);
return guiyesno;
}
@Override
public void drawScreen(int mouseX, int mouseY, float partialTicks) {
this.drawDefaultBackground();
this.drawCenteredString(fontRendererObj, "Replay Center", this.width/2, 8, Color.WHITE.getRGB());
super.drawScreen(mouseX, mouseY, partialTicks);
}
@Override
public void onGuiClosed() {
Keyboard.enableRepeatEvents(false);
}
public void showOverview() {
mc.addScheduledTask(new Runnable() {
@Override
public void run() {
try {
FileInfo[] files = ReplayMod.apiClient.getRecentFiles();
for(FileInfo i : files) {
//TODO: Display the Files
}
} catch (IOException e) {
e.printStackTrace();
} catch (ApiException e) { //TODO: Error message
e.printStackTrace();
}
}
});
}
} }

View File

@@ -275,8 +275,7 @@ public class GuiReplayManager extends GuiScreen implements GuiYesNoCallback {
} }
} }
public static GuiYesNo getYesNoGui(GuiYesNoCallback p_152129_0_, String file, int p_152129_2_) public static GuiYesNo getYesNoGui(GuiYesNoCallback p_152129_0_, String file, int p_152129_2_) {
{
String s1 = I18n.format("Are you sure you want to delete this replay?", new Object[0]); String s1 = I18n.format("Are you sure you want to delete this replay?", new Object[0]);
String s2 = "\'" + file + "\' " + I18n.format("will be lost forever! (A long time!)", new Object[0]); String s2 = "\'" + file + "\' " + I18n.format("will be lost forever! (A long time!)", new Object[0]);
String s3 = I18n.format("Delete", new Object[0]); String s3 = I18n.format("Delete", new Object[0]);

View File

@@ -1,6 +1,5 @@
package eu.crushedpixel.replaymod.online.authentication; package eu.crushedpixel.replaymod.online.authentication;
import java.io.IOException;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
@@ -23,6 +22,10 @@ public class AuthenticationHandler {
return authkey != null; return authkey != null;
} }
public static String getKey() {
return authkey;
}
public static int authenticate(String username, String password) { public static int authenticate(String username, String password) {
try { try {
authkey = ReplayMod.apiClient.getLogin(username, password).getAuthkey(); authkey = ReplayMod.apiClient.getLogin(username, password).getAuthkey();
@@ -34,6 +37,18 @@ public class AuthenticationHandler {
} }
} }
public static int logout() {
try {
boolean success = ReplayMod.apiClient.logout(authkey);
authkey = null;
return SUCCESS;
} catch(ApiException e) {
return INVALID;
} catch(Exception e) {
return NO_CONNECTION;
}
}
private static final List<String> PREMIUM_USERS = new ArrayList<String>() { private static final List<String> PREMIUM_USERS = new ArrayList<String>() {
{ {
add("Ender_Workbench"); add("Ender_Workbench");