+ The 'YT' button is back

+ Now adds protocol automatically on URLs
* Fix of remote URL peripheral
* Updated README
This commit is contained in:
Nicolas BARBOTIN 2018-02-04 00:37:06 +01:00
parent ce2c1d881f
commit 3136dd7697
14 changed files with 283 additions and 117 deletions

View File

@ -7,14 +7,10 @@ This is the unfinished port of the WebDisplays mod for Minecraft 1.12.2. The tex
* Read config (see "Config elements" below) * Read config (see "Config elements" below)
### TODO ### TODO
* GuiSetURL2 missing buttons
* Automatically add protocol to URLs
* Using the remote control tool too far away (with a chunk loader ofc) may trigger distance guard in SMessageScreenCtrl
* French translations * French translations
* minePad management: check GuiContainer.draggedStack for minePad * minePad management: check GuiContainer.draggedStack for minePad
* Change mod name to WD2 * Change mod name to WD2
* Put a limit on screen resolution * Put a limit on screen resolution
* YT button (also add it to the redstone controller gui)
### Config elements ### Config elements
* Site blacklist * Site blacklist

View File

@ -19,10 +19,7 @@ import net.montoyo.wd.core.IUpgrade;
import net.montoyo.wd.core.JSServerRequest; import net.montoyo.wd.core.JSServerRequest;
import net.montoyo.wd.entity.TileEntityScreen; import net.montoyo.wd.entity.TileEntityScreen;
import net.montoyo.wd.net.SMessageScreenCtrl; import net.montoyo.wd.net.SMessageScreenCtrl;
import net.montoyo.wd.utilities.BlockSide; import net.montoyo.wd.utilities.*;
import net.montoyo.wd.utilities.Log;
import net.montoyo.wd.utilities.Vector2i;
import net.montoyo.wd.utilities.Vector3i;
import java.util.ArrayDeque; import java.util.ArrayDeque;
import java.util.ArrayList; import java.util.ArrayList;
@ -336,7 +333,7 @@ public final class JSQueryDispatcher {
sb.append(','); sb.append(',');
sb.append('\"'); sb.append('\"');
sb.append(((IUpgrade) upgrades.get(i).getItem()).getJSName(upgrades.get(i))); sb.append(Util.addSlashes(((IUpgrade) upgrades.get(i).getItem()).getJSName(upgrades.get(i))));
sb.append('\"'); sb.append('\"');
} }

View File

@ -10,6 +10,7 @@ import net.montoyo.wd.client.gui.controls.Button;
import net.montoyo.wd.client.gui.controls.TextField; import net.montoyo.wd.client.gui.controls.TextField;
import net.montoyo.wd.client.gui.loading.FillControl; import net.montoyo.wd.client.gui.loading.FillControl;
import net.montoyo.wd.net.SMessageRedstoneCtrl; import net.montoyo.wd.net.SMessageRedstoneCtrl;
import net.montoyo.wd.utilities.Util;
import net.montoyo.wd.utilities.Vector3i; import net.montoyo.wd.utilities.Vector3i;
public class GuiRedstoneCtrl extends WDScreen { public class GuiRedstoneCtrl extends WDScreen {
@ -48,8 +49,11 @@ public class GuiRedstoneCtrl extends WDScreen {
@GuiSubscribe @GuiSubscribe
public void onClick(Button.ClickEvent ev) { public void onClick(Button.ClickEvent ev) {
if(ev.getSource() == btnOk) if(ev.getSource() == btnOk) {
WebDisplays.NET_HANDLER.sendToServer(new SMessageRedstoneCtrl(dimension, pos, tfRisingEdge.getText(), tfFallingEdge.getText())); String rising = Util.addProtocol(tfRisingEdge.getText());
String falling = Util.addProtocol(tfFallingEdge.getText());
WebDisplays.NET_HANDLER.sendToServer(new SMessageRedstoneCtrl(dimension, pos, rising, falling));
}
mc.displayGuiScreen(null); mc.displayGuiScreen(null);
} }

View File

@ -13,7 +13,8 @@ import net.montoyo.wd.entity.TileEntityScreen;
import net.montoyo.wd.net.SMessagePadCtrl; import net.montoyo.wd.net.SMessagePadCtrl;
import net.montoyo.wd.net.SMessageScreenCtrl; import net.montoyo.wd.net.SMessageScreenCtrl;
import net.montoyo.wd.utilities.BlockSide; import net.montoyo.wd.utilities.BlockSide;
import net.montoyo.wd.utilities.Log; import net.montoyo.wd.utilities.Util;
import net.montoyo.wd.utilities.Vector3i;
import java.util.Map; import java.util.Map;
@ -22,6 +23,7 @@ public class GuiSetURL2 extends WDScreen {
//Screen data //Screen data
private TileEntityScreen tileEntity; private TileEntityScreen tileEntity;
private BlockSide screenSide; private BlockSide screenSide;
private Vector3i remoteLocation;
//Pad data //Pad data
private boolean isPad; private boolean isPad;
@ -41,19 +43,17 @@ public class GuiSetURL2 extends WDScreen {
@FillControl @FillControl
private Button btnOk; private Button btnOk;
@FillControl public GuiSetURL2(TileEntityScreen tes, BlockSide side, String url, Vector3i rl) {
private Button btnYT;
public GuiSetURL2(TileEntityScreen tes, BlockSide side, String url) {
tileEntity = tes; tileEntity = tes;
screenSide = side; screenSide = side;
screenURL = url; remoteLocation = rl;
isPad = false; isPad = false;
screenURL = url;
} }
public GuiSetURL2(String url) { public GuiSetURL2(String url) {
screenURL = url;
isPad = true; isPad = true;
screenURL = url;
} }
@Override @Override
@ -79,8 +79,7 @@ public class GuiSetURL2 extends WDScreen {
WebDisplays.NET_HANDLER.sendToServer(new SMessagePadCtrl("")); WebDisplays.NET_HANDLER.sendToServer(new SMessagePadCtrl(""));
mc.displayGuiScreen(null); mc.displayGuiScreen(null);
} else }
Log.info("GuiSetURL2: TODO"); //TODO
} }
@GuiSubscribe @GuiSubscribe
@ -90,10 +89,12 @@ public class GuiSetURL2 extends WDScreen {
private void validate(String url) { private void validate(String url) {
if(!url.isEmpty()) { if(!url.isEmpty()) {
url = Util.addProtocol(url);
if(isPad) if(isPad)
WebDisplays.NET_HANDLER.sendToServer(new SMessagePadCtrl(url)); WebDisplays.NET_HANDLER.sendToServer(new SMessagePadCtrl(url));
else else
WebDisplays.NET_HANDLER.sendToServer(new SMessageScreenCtrl(tileEntity, screenSide, url)); WebDisplays.NET_HANDLER.sendToServer(SMessageScreenCtrl.setURL(tileEntity, screenSide, url, remoteLocation));
} }
mc.displayGuiScreen(null); mc.displayGuiScreen(null);

View File

@ -12,11 +12,11 @@ import java.io.IOException;
public class Button extends Control { public class Button extends Control {
private final GuiButton btn; protected final GuiButton btn;
private boolean selected = false; protected boolean selected = false;
private boolean shiftDown = false; protected boolean shiftDown = false;
private int originalColor = 0; protected int originalColor = 0;
private int shiftColor = 0; protected int shiftColor = 0;
public static class ClickEvent extends Event<Button> { public static class ClickEvent extends Event<Button> {
@ -50,7 +50,9 @@ public class Button extends Control {
if(mouseButton == 0 && btn.mousePressed(mc, mouseX, mouseY)) { if(mouseButton == 0 && btn.mousePressed(mc, mouseX, mouseY)) {
selected = true; selected = true;
btn.playPressSound(mc.getSoundHandler()); btn.playPressSound(mc.getSoundHandler());
parent.actionPerformed(new ClickEvent(this));
if(!onClick())
parent.actionPerformed(new ClickEvent(this));
} }
} }
@ -187,13 +189,17 @@ public class Button extends Control {
btn.x = json.getInt("x", 0); btn.x = json.getInt("x", 0);
btn.y = json.getInt("y", 0); btn.y = json.getInt("y", 0);
btn.width = json.getInt("width", 200); btn.width = json.getInt("width", 200);
btn.displayString = tr(json.getString("label", "")); btn.displayString = tr(json.getString("label", btn.displayString));
btn.enabled = !json.getBool("disabled", false); btn.enabled = !json.getBool("disabled", !btn.enabled);
btn.visible = json.getBool("visible", true); btn.visible = json.getBool("visible", btn.visible);
originalColor = json.getColor("color", 0); originalColor = json.getColor("color", originalColor);
shiftColor = json.getColor("shiftColor", 0); shiftColor = json.getColor("shiftColor", shiftColor);
btn.packedFGColour = originalColor; btn.packedFGColour = originalColor;
} }
protected boolean onClick() {
return false;
}
} }

View File

@ -9,6 +9,7 @@ import net.montoyo.wd.client.gui.loading.JsonOWrapper;
import org.lwjgl.input.Keyboard; import org.lwjgl.input.Keyboard;
import java.io.IOException; import java.io.IOException;
import java.util.ArrayList;
public class TextField extends Control { public class TextField extends Control {
@ -75,6 +76,12 @@ public class TextField extends Control {
} }
public interface TextChangeListener {
void onTextChange(TextField tf, String oldContent, String newContent);
}
public static final int DEFAULT_TEXT_COLOR = 14737632; public static final int DEFAULT_TEXT_COLOR = 14737632;
public static final int DEFAULT_DISABLED_COLOR = 7368816; public static final int DEFAULT_DISABLED_COLOR = 7368816;
@ -82,6 +89,7 @@ public class TextField extends Control {
private boolean enabled = true; private boolean enabled = true;
private int textColor = DEFAULT_TEXT_COLOR; private int textColor = DEFAULT_TEXT_COLOR;
private int disabledColor = DEFAULT_DISABLED_COLOR; private int disabledColor = DEFAULT_DISABLED_COLOR;
private ArrayList<TextChangeListener> listeners = new ArrayList<>();
public TextField() { public TextField() {
field = new GuiTextField(0, font, 1, 1, 198, 20); field = new GuiTextField(0, font, 1, 1, 198, 20);
@ -111,8 +119,12 @@ public class TextField extends Control {
field.textboxKeyTyped(typedChar, keyCode); field.textboxKeyTyped(typedChar, keyCode);
if(enabled && field.isFocused() && !field.getText().equals(old)) if(enabled && field.isFocused() && !field.getText().equals(old)) {
for(TextChangeListener tcl : listeners)
tcl.onTextChange(this, old, field.getText());
parent.actionPerformed(new TextChangedEvent(this, old)); parent.actionPerformed(new TextChangedEvent(this, old));
}
} }
} }
@ -127,7 +139,13 @@ public class TextField extends Control {
} }
public void setText(String text) { public void setText(String text) {
String old = field.getText();
field.setText(text); field.setText(text);
if(!old.equals(text)) {
for(TextChangeListener tcl : listeners)
tcl.onTextChange(this, old, text);
}
} }
public void clear() { public void clear() {
@ -258,6 +276,15 @@ public class TextField extends Control {
return field; return field;
} }
public void addTextChangeListener(TextChangeListener l) {
if(l != null && !listeners.contains(l))
listeners.add(l);
}
public void removeTextChangeListener(TextChangeListener l) {
listeners.remove(l);
}
@Override @Override
public void load(JsonOWrapper json) { public void load(JsonOWrapper json) {
super.load(json); super.load(json);

View File

@ -0,0 +1,78 @@
/*
* Copyright (C) 2018 BARBOTIN Nicolas
*/
package net.montoyo.wd.client.gui.controls;
import net.montoyo.wd.client.gui.loading.JsonOWrapper;
import net.montoyo.wd.utilities.Util;
import net.montoyo.wd.utilities.VideoType;
import java.net.MalformedURLException;
import java.net.URL;
public class YTButton extends Button implements TextField.TextChangeListener {
private TextField urlField;
public YTButton() {
btn.displayString = "YT";
btn.enabled = false;
shiftColor = 0xFFFF6464;
}
@Override
protected boolean onClick() {
if(urlField != null) {
String urlStr = Util.addProtocol(urlField.getText());
URL url;
try {
url = new URL(urlStr);
} catch(MalformedURLException ex) {
return true;
}
VideoType vt = VideoType.getTypeFromURL(url);
if(vt == VideoType.YOUTUBE)
urlField.setText(VideoType.YOUTUBE_EMBED.getURLFromID(vt.getVideoIDFromURL(url), shiftDown));
}
return true;
}
public void setURLField(TextField tf) {
if(urlField != null)
tf.removeTextChangeListener(this);
urlField = tf;
if(urlField != null)
tf.addTextChangeListener(this);
}
public TextField getURLField() {
return urlField;
}
@Override
public void load(JsonOWrapper json) {
super.load(json);
String tfName = json.getString("urlField", null);
if(tfName != null) {
Control ctrl = parent.getControlByName(tfName);
if(ctrl != null && ctrl instanceof TextField) {
urlField = (TextField) ctrl;
urlField.addTextChangeListener(this);
}
}
}
@Override
public void onTextChange(TextField tf, String oldContent, String newContent) {
btn.enabled = (VideoType.getTypeFromURL(Util.addProtocol(newContent)) == VideoType.YOUTUBE);
}
}

View File

@ -43,6 +43,7 @@ public class GuiLoader {
register(TextField.class); register(TextField.class);
register(Icon.class); register(Icon.class);
register(UpgradeGroup.class); register(UpgradeGroup.class);
register(YTButton.class);
} }
public static Control create(JsonOWrapper json) { public static Control create(JsonOWrapper json) {

View File

@ -6,6 +6,7 @@ package net.montoyo.wd.data;
import net.minecraft.client.gui.GuiScreen; import net.minecraft.client.gui.GuiScreen;
import net.minecraft.tileentity.TileEntity; import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World; import net.minecraft.world.World;
import net.minecraftforge.fml.relauncher.Side; import net.minecraftforge.fml.relauncher.Side;
import net.minecraftforge.fml.relauncher.SideOnly; import net.minecraftforge.fml.relauncher.SideOnly;
@ -20,6 +21,8 @@ public class SetURLData extends GuiData {
public Vector3i pos; public Vector3i pos;
public BlockSide side; public BlockSide side;
public String url; public String url;
public boolean isRemote;
public Vector3i remoteLocation;
public SetURLData() { public SetURLData() {
} }
@ -28,6 +31,16 @@ public class SetURLData extends GuiData {
this.pos = pos; this.pos = pos;
this.side = side; this.side = side;
this.url = url; this.url = url;
isRemote = false;
remoteLocation = new Vector3i();
}
public SetURLData(Vector3i pos, BlockSide side, String url, BlockPos rl) {
this.pos = pos;
this.side = side;
this.url = url;
isRemote = true;
remoteLocation = new Vector3i(rl);
} }
@SideOnly(Side.CLIENT) @SideOnly(Side.CLIENT)
@ -39,7 +52,7 @@ public class SetURLData extends GuiData {
return null; return null;
} }
return new GuiSetURL2((TileEntityScreen) te, side, url); return new GuiSetURL2((TileEntityScreen) te, side, url, isRemote ? remoteLocation : null);
} }
@Override @Override

View File

@ -36,7 +36,7 @@ public class TileEntityRCtrl extends TileEntityPeripheralBase {
return true; return true;
} }
(new SetURLData(screenPos, screenSide, scr.url)).sendTo((EntityPlayerMP) player); (new SetURLData(screenPos, screenSide, scr.url, pos)).sendTo((EntityPlayerMP) player);
return true; return true;
} }

View File

@ -5,6 +5,8 @@
package net.montoyo.wd.net; package net.montoyo.wd.net;
import io.netty.buffer.ByteBuf; import io.netty.buffer.ByteBuf;
import net.minecraft.block.state.IBlockState;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.entity.player.EntityPlayerMP; import net.minecraft.entity.player.EntityPlayerMP;
import net.minecraft.item.ItemStack; import net.minecraft.item.ItemStack;
import net.minecraft.tileentity.TileEntity; import net.minecraft.tileentity.TileEntity;
@ -16,6 +18,9 @@ import net.minecraftforge.fml.common.network.simpleimpl.IMessage;
import net.minecraftforge.fml.common.network.simpleimpl.IMessageHandler; import net.minecraftforge.fml.common.network.simpleimpl.IMessageHandler;
import net.minecraftforge.fml.common.network.simpleimpl.MessageContext; import net.minecraftforge.fml.common.network.simpleimpl.MessageContext;
import net.minecraftforge.fml.relauncher.Side; import net.minecraftforge.fml.relauncher.Side;
import net.montoyo.wd.WebDisplays;
import net.montoyo.wd.block.BlockPeripheral;
import net.montoyo.wd.core.DefaultPeripheral;
import net.montoyo.wd.core.JSServerRequest; import net.montoyo.wd.core.JSServerRequest;
import net.montoyo.wd.core.MissingPermissionException; import net.montoyo.wd.core.MissingPermissionException;
import net.montoyo.wd.core.ScreenRights; import net.montoyo.wd.core.ScreenRights;
@ -38,6 +43,7 @@ public class SMessageScreenCtrl implements IMessage, Runnable {
public static final int CTRL_LASER_UP = 10; public static final int CTRL_LASER_UP = 10;
public static final int CTRL_JS_REQUEST = 11; public static final int CTRL_JS_REQUEST = 11;
public static final int CTRL_SET_ROTATION = 12; public static final int CTRL_SET_ROTATION = 12;
public static final int CTRL_SET_URL_REMOTE = 13;
private int ctrl; private int ctrl;
private int dim; private int dim;
@ -56,24 +62,23 @@ public class SMessageScreenCtrl implements IMessage, Runnable {
private JSServerRequest jsReqType; private JSServerRequest jsReqType;
private Object[] jsReqData; private Object[] jsReqData;
private Rotation rotation; private Rotation rotation;
private Vector3i remoteLoc;
public SMessageScreenCtrl() { public SMessageScreenCtrl() {
} }
public SMessageScreenCtrl(TileEntityScreen tes, BlockSide side, String url) { public static SMessageScreenCtrl setURL(TileEntityScreen tes, BlockSide side, String url, Vector3i remoteLocation) {
ctrl = CTRL_SET_URL; SMessageScreenCtrl ret = new SMessageScreenCtrl();
dim = tes.getWorld().provider.getDimension(); ret.ctrl = (remoteLocation == null) ? CTRL_SET_URL : CTRL_SET_URL_REMOTE;
pos = new Vector3i(tes.getPos()); ret.dim = tes.getWorld().provider.getDimension();
this.side = side; ret.pos = new Vector3i(tes.getPos());
this.url = url; ret.side = side;
} ret.url = url;
public SMessageScreenCtrl(TileEntityScreen tes, BlockSide side) { if(remoteLocation != null)
ctrl = CTRL_SHUT_DOWN; ret.remoteLoc = remoteLocation;
dim = tes.getWorld().provider.getDimension();
pos = new Vector3i(tes.getPos()); return ret;
this.side = side;
this.url = url;
} }
public SMessageScreenCtrl(TileEntityScreen tes, BlockSide side, NameUUIDPair friend, boolean del) { public SMessageScreenCtrl(TileEntityScreen tes, BlockSide side, NameUUIDPair friend, boolean del) {
@ -195,6 +200,10 @@ public class SMessageScreenCtrl implements IMessage, Runnable {
jsReqData = jsReqType.deserialize(buf); jsReqData = jsReqType.deserialize(buf);
} else if(ctrl == CTRL_SET_ROTATION) } else if(ctrl == CTRL_SET_ROTATION)
rotation = Rotation.values()[buf.readByte() & 3]; rotation = Rotation.values()[buf.readByte() & 3];
else if(ctrl == CTRL_SET_URL_REMOTE) {
url = ByteBufUtils.readUTF8String(buf);
remoteLoc = new Vector3i(buf);
}
} }
@Override @Override
@ -228,6 +237,10 @@ public class SMessageScreenCtrl implements IMessage, Runnable {
throw new RuntimeException("Could not serialize CTRL_JS_REQUEST " + jsReqType); throw new RuntimeException("Could not serialize CTRL_JS_REQUEST " + jsReqType);
} else if(ctrl == CTRL_SET_ROTATION) } else if(ctrl == CTRL_SET_ROTATION)
buf.writeByte(rotation.ordinal()); buf.writeByte(rotation.ordinal());
else if(ctrl == CTRL_SET_URL_REMOTE) {
ByteBufUtils.writeUTF8String(buf, url);
remoteLoc.writeTo(buf);
}
} }
@Override @Override
@ -254,8 +267,21 @@ public class SMessageScreenCtrl implements IMessage, Runnable {
World world = player.world; World world = player.world;
BlockPos bp = pos.toBlock(); BlockPos bp = pos.toBlock();
if(world.provider.getDimension() != dim || player.getDistanceSq(bp) > 512.0 * 512.0) if(world.provider.getDimension() != dim)
return; //Out of range return; //Out of range (dimension mismatch)
if(ctrl == CTRL_SET_URL_REMOTE) {
double reachDist = player.getEntityAttribute(EntityPlayer.REACH_DISTANCE).getAttributeValue();
BlockPos blockPos = remoteLoc.toBlock();
if(player.getDistanceSq(blockPos) > reachDist * reachDist)
return; //Out of range (player reach distance)
IBlockState bs = world.getBlockState(blockPos);
if(bs.getBlock() != WebDisplays.INSTANCE.blockPeripheral || bs.getValue(BlockPeripheral.type) != DefaultPeripheral.REMOTE_CONTROLLER)
return; //I call it hax...
} else if(player.getDistanceSq(bp) > 128.0 * 128.0)
return; //Out of range (range problem)
TileEntity te = world.getTileEntity(bp); TileEntity te = world.getTileEntity(bp);
if(te == null || !(te instanceof TileEntityScreen)) { if(te == null || !(te instanceof TileEntityScreen)) {
@ -265,12 +291,13 @@ public class SMessageScreenCtrl implements IMessage, Runnable {
TileEntityScreen tes = (TileEntityScreen) te; TileEntityScreen tes = (TileEntityScreen) te;
if(ctrl == CTRL_SET_URL) { if(ctrl == CTRL_SET_URL || ctrl == CTRL_SET_URL_REMOTE) {
checkPermission(tes, ScreenRights.CHANGE_URL); checkPermission(tes, ScreenRights.CHANGE_URL);
tes.setScreenURL(side, url); tes.setScreenURL(side, url);
} else if(ctrl == CTRL_SHUT_DOWN) { } else if(ctrl == CTRL_SHUT_DOWN) {
checkPermission(tes, ScreenRights.CHANGE_URL); //TODO
tes.removeScreen(side); //checkPermission(tes, ScreenRights.CHANGE_URL);
//tes.removeScreen(side);
} else if(ctrl == CTRL_ADD_FRIEND) { } else if(ctrl == CTRL_ADD_FRIEND) {
checkPermission(tes, ScreenRights.MANAGE_FRIEND_LIST); checkPermission(tes, ScreenRights.MANAGE_FRIEND_LIST);
tes.addFriend(player, side, friend); tes.addFriend(player, side, friend);

View File

@ -38,12 +38,12 @@ public abstract class Util {
Object[] ray = (Object[]) f; Object[] ray = (Object[]) f;
bb.writeInt(ray.length); bb.writeInt(ray.length);
for(Object o: ray) for(Object o : ray)
serialize(bb, o); serialize(bb, o);
} else if(!cls.isPrimitive()) { } else if(!cls.isPrimitive()) {
Field[] fields = cls.getFields(); Field[] fields = cls.getFields();
for(Field ff: fields) { for(Field ff : fields) {
try { try {
if(ff.getAnnotation(DontSerialize.class) == null && !Modifier.isStatic(ff.getModifiers())) if(ff.getAnnotation(DontSerialize.class) == null && !Modifier.isStatic(ff.getModifiers()))
serialize(bb, ff.get(f)); serialize(bb, ff.get(f));
@ -92,7 +92,7 @@ public abstract class Util {
throw new RuntimeException(String.format("Caught IllegalAccessException for class %s", cls.getName())); throw new RuntimeException(String.format("Caught IllegalAccessException for class %s", cls.getName()));
} }
for(Field ff: fields) { for(Field ff : fields) {
try { try {
if(ff.getAnnotation(DontSerialize.class) == null && !Modifier.isStatic(ff.getModifiers())) if(ff.getAnnotation(DontSerialize.class) == null && !Modifier.isStatic(ff.getModifiers()))
ff.set(ret, unserialize(bb, ff.getType())); ff.set(ret, unserialize(bb, ff.getType()));
@ -123,7 +123,7 @@ public abstract class Util {
Object[] ray = (Object[]) f; Object[] ray = (Object[]) f;
NBTTagList ret = new NBTTagList(); NBTTagList ret = new NBTTagList();
for(Object o: ray) for(Object o : ray)
ret.appendTag(serialize(o)); ret.appendTag(serialize(o));
return ret; return ret;
@ -197,17 +197,16 @@ public abstract class Util {
return out; return out;
} }
public static int scrambleKey(int idx) public static int scrambleKey(int idx) {
{
idx = idx * 0x9E3779B9; idx = idx * 0x9E3779B9;
return idx ^ (idx >> 16); return idx ^ (idx >> 16);
} }
public static void toast(EntityPlayer player, String key, Object ... data) { public static void toast(EntityPlayer player, String key, Object... data) {
toast(player, TextFormatting.RED, key, data); toast(player, TextFormatting.RED, key, data);
} }
public static void toast(EntityPlayer player, TextFormatting color, String key, Object ... data) { public static void toast(EntityPlayer player, TextFormatting color, String key, Object... data) {
ITextComponent root = new TextComponentString("[WebDisplays] "); ITextComponent root = new TextComponentString("[WebDisplays] ");
root.setStyle((new Style()).setColor(color)); root.setStyle((new Style()).setColor(color));
root.appendSibling(new TextComponentTranslation("webdisplays.message." + key, data)); root.appendSibling(new TextComponentTranslation("webdisplays.message." + key, data));
@ -221,4 +220,8 @@ public abstract class Util {
} catch(Throwable t) {} } catch(Throwable t) {}
} }
public static String addProtocol(String str) {
return str.contains("://") ? str : ("http://" + str);
}
} }

View File

@ -15,7 +15,15 @@
"name": "tfRisingEdge", "name": "tfRisingEdge",
"x": 20, "x": 20,
"y": 0, "y": 0,
"width": 280 "width": 280,
"maxLength": 65535
},
{
"type": "YTButton",
"x": 305,
"y": 0,
"width": 20,
"urlField": "tfRisingEdge"
}, },
{ {
"type": "Icon", "type": "Icon",
@ -32,7 +40,15 @@
"name": "tfFallingEdge", "name": "tfFallingEdge",
"x": 20, "x": 20,
"y": 24, "y": 24,
"width": 280 "width": 280,
"maxLength": 65535
},
{
"type": "YTButton",
"x": 305,
"y": 24,
"width": 20,
"urlField": "tfFallingEdge"
}, },
{ {
"type": "Button", "type": "Button",

View File

@ -1,56 +1,53 @@
{ {
"controls": [ "controls": [
{ {
"type": "Label", "type": "Label",
"label": "$webdisplays.gui.seturl.url", "label": "$webdisplays.gui.seturl.url",
"x": 0, "x": 0,
"y": 0, "y": 0,
"shadowed": true "shadowed": true
}, },
{ {
"type": "TextField", "type": "TextField",
"name": "tfURL", "name": "tfURL",
"x": 0, "x": 0,
"y": 12, "y": 12,
"width": 272, "width": 272,
"maxLength": 65535 "maxLength": 65535
}, },
{ {
"type": "Button", "type": "YTButton",
"name": "btnYT", "x": 276,
"label": "YT", "y": 13,
"x": 276, "width": 20,
"y": 13, "urlField": "tfURL"
"width": 20, },
"shiftColor": [ 255, 100, 100 ] {
}, "type": "Button",
{ "name": "btnShutDown",
"type": "Button", "label": "$webdisplays.gui.seturl.shutdown",
"name": "btnShutDown", "x": 0,
"label": "$webdisplays.gui.seturl.shutdown", "y": 38,
"x": 0, "width": 96,
"y": 38, "visible": "isPad",
"width": 96, "disabled": "1 - isPad"
"visible": "isPad", },
"disabled": "1 - isPad" {
}, "type": "Button",
{ "name": "btnCancel",
"type": "Button", "label": "$webdisplays.gui.seturl.cancel",
"name": "btnCancel", "x": "isPad & 100 | 0",
"label": "$webdisplays.gui.seturl.cancel", "y": 38,
"x": "isPad & 100 | 0", "width": "isPad & 96 | 146"
"y": 38, },
"width": "isPad & 96 | 146" {
}, "type": "Button",
{ "name": "btnOk",
"type": "Button", "label": "$webdisplays.gui.seturl.ok",
"name": "btnOk", "x": "isPad & 200 | 150",
"label": "$webdisplays.gui.seturl.ok", "y": 38,
"x": "isPad & 200 | 150", "width": "isPad & 96 | 146"
"y": 38, }
"width": "isPad & 96 | 146" ],
} "center": true
],
"center": true
} }