diff --git a/patches/minecraft/net/minecraft/network/NetHandlerPlayServer.java.patch b/patches/minecraft/net/minecraft/network/NetHandlerPlayServer.java.patch index cc1d23ada..9738d4cbf 100644 --- a/patches/minecraft/net/minecraft/network/NetHandlerPlayServer.java.patch +++ b/patches/minecraft/net/minecraft/network/NetHandlerPlayServer.java.patch @@ -151,10 +151,12 @@ { this.func_147359_a(new S2FPacketSetSlot(this.field_147369_b.field_71070_bA.field_75152_c, slot.field_75222_d, this.field_147369_b.field_71071_by.func_70448_g())); } -@@ -677,6 +720,8 @@ +@@ -676,7 +719,9 @@ + } else { - ChatComponentTranslation chatcomponenttranslation1 = new ChatComponentTranslation("chat.type.text", new Object[] {this.field_147369_b.func_145748_c_(), s}); +- ChatComponentTranslation chatcomponenttranslation1 = new ChatComponentTranslation("chat.type.text", new Object[] {this.field_147369_b.func_145748_c_(), s}); ++ ChatComponentTranslation chatcomponenttranslation1 = new ChatComponentTranslation("chat.type.text", new Object[] {this.field_147369_b.func_145748_c_(), ForgeHooks.newChatWithLinks(s)}); // Fixes chat links + chatcomponenttranslation1 = ForgeHooks.onServerChatEvent(this, s, chatcomponenttranslation1); + if (chatcomponenttranslation1 == null) return; this.field_147367_d.func_71203_ab().func_148544_a(chatcomponenttranslation1, false); diff --git a/src/main/java/net/minecraftforge/common/ForgeHooks.java b/src/main/java/net/minecraftforge/common/ForgeHooks.java index 8dd69ba50..b3e5a0422 100644 --- a/src/main/java/net/minecraftforge/common/ForgeHooks.java +++ b/src/main/java/net/minecraftforge/common/ForgeHooks.java @@ -1,8 +1,11 @@ package net.minecraftforge.common; +import java.net.URI; import java.util.ArrayList; import java.util.List; import java.util.Set; +import java.util.regex.Matcher; +import java.util.regex.Pattern; import cpw.mods.fml.common.eventhandler.Event; import cpw.mods.fml.relauncher.ReflectionHelper; @@ -11,6 +14,7 @@ import net.minecraft.entity.EntityLivingBase; import net.minecraft.entity.item.EntityItem; import net.minecraft.entity.player.EntityPlayer; import net.minecraft.entity.player.EntityPlayerMP; +import net.minecraft.event.ClickEvent; import net.minecraft.init.Blocks; import net.minecraft.init.Items; import net.minecraft.inventory.Container; @@ -32,8 +36,10 @@ import net.minecraft.stats.StatList; import net.minecraft.tileentity.TileEntity; import net.minecraft.tileentity.TileEntityNote; import net.minecraft.util.AxisAlignedBB; +import net.minecraft.util.ChatComponentText; import net.minecraft.util.ChatComponentTranslation; import net.minecraft.util.DamageSource; +import net.minecraft.util.IChatComponent; import net.minecraft.util.MathHelper; import net.minecraft.util.MovingObjectPosition; import net.minecraft.util.MovingObjectPosition.MovingObjectType; @@ -380,6 +386,50 @@ public class ForgeHooks return event.component; } + public static IChatComponent newChatWithLinks(String string) + { + // Includes ipv4 and domain pattern + // Matches an ip (xx.xxx.xx.xxx) or a domain (something.com) with or + // without a protocol or path. + final Pattern URL_PATTERN = Pattern.compile( + // schema ipv4 OR namespace port path ends + // |-----------------| |-------------------------| |----------------------------| |---------| |--| |---------------| + "((?:[a-z0-9]{2,}:\\/\\/)?(?:(?:[0-9]{1,3}\\.){3}[0-9]{1,3}|(?:[-\\w_\\.]{1,}\\.[a-z]{2,}?))(?::[0-9]{1,5})?.*?(?=[!\"\u00A7 \n]|$))", + Pattern.CASE_INSENSITIVE); + IChatComponent ichat = new ChatComponentText(""); + Matcher matcher = URL_PATTERN.matcher(string); + int lastEnd = 0; + String remaining = string; + + // Find all urls + while (matcher.find()) + { + int start = matcher.start(); + int end = matcher.end(); + + // Append the previous left overs. + ichat.appendText(string.substring(lastEnd, start)); + lastEnd = end; + String url = string.substring(start, end); + IChatComponent link = new ChatComponentText(url); + + // Add schema so client doesn't crash. + if (URI.create(url).getScheme() == null) + { + url = "http://" + url; + } + + // Set the click event and append the link. + ClickEvent click = new ClickEvent(ClickEvent.Action.OPEN_URL, url); + link.getChatStyle().setChatClickEvent(click); + ichat.appendSibling(link); + } + + // Append the rest of the message. + ichat.appendText(string.substring(lastEnd)); + return ichat; + } + public static boolean canInteractWith(EntityPlayer player, Container openContainer) { PlayerOpenContainerEvent event = new PlayerOpenContainerEvent(player, openContainer);