client: add ability to inject custom cs2 scripts
This commit is contained in:
@@ -1894,6 +1894,14 @@ public interface Client extends OAuthApi, GameEngine
|
|||||||
*/
|
*/
|
||||||
void setBlacklistDeadNpcs(Set<Integer> blacklist);
|
void setBlacklistDeadNpcs(Set<Integer> blacklist);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Adds a custom clientscript to the list of available clientscripts.
|
||||||
|
*
|
||||||
|
* @param script compiled clientscript code
|
||||||
|
* @return the id of the newly-added script
|
||||||
|
*/
|
||||||
|
int addClientScript(byte[] script);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets an array of tile collision data.
|
* Gets an array of tile collision data.
|
||||||
* <p>
|
* <p>
|
||||||
|
|||||||
@@ -29,11 +29,13 @@ import java.io.IOException;
|
|||||||
import java.io.InputStream;
|
import java.io.InputStream;
|
||||||
import java.util.HashSet;
|
import java.util.HashSet;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
|
import lombok.Getter;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
|
||||||
@Slf4j
|
@Slf4j
|
||||||
public class OverlayIndex
|
public class OverlayIndex
|
||||||
{
|
{
|
||||||
|
@Getter
|
||||||
private static final Set<Integer> overlays = new HashSet<>();
|
private static final Set<Integer> overlays = new HashSet<>();
|
||||||
|
|
||||||
static
|
static
|
||||||
|
|||||||
@@ -1,14 +1,11 @@
|
|||||||
package net.runelite.mixins;
|
package net.runelite.mixins;
|
||||||
|
|
||||||
import com.google.common.base.Charsets;
|
|
||||||
import com.google.common.hash.Hashing;
|
import com.google.common.hash.Hashing;
|
||||||
import com.google.common.io.ByteStreams;
|
import com.google.common.io.ByteStreams;
|
||||||
import com.google.common.io.CharStreams;
|
import com.google.common.io.CharStreams;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.InputStream;
|
import java.io.InputStream;
|
||||||
import java.io.InputStreamReader;
|
import java.io.InputStreamReader;
|
||||||
import java.util.HashMap;
|
|
||||||
import java.util.List;
|
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import net.runelite.api.mixins.Copy;
|
import net.runelite.api.mixins.Copy;
|
||||||
import net.runelite.api.mixins.Inject;
|
import net.runelite.api.mixins.Inject;
|
||||||
@@ -19,7 +16,6 @@ import net.runelite.api.overlay.OverlayIndex;
|
|||||||
import net.runelite.rs.api.RSAbstractArchive;
|
import net.runelite.rs.api.RSAbstractArchive;
|
||||||
import net.runelite.rs.api.RSArchive;
|
import net.runelite.rs.api.RSArchive;
|
||||||
import net.runelite.rs.api.RSClient;
|
import net.runelite.rs.api.RSClient;
|
||||||
import org.apache.commons.io.IOUtils;
|
|
||||||
import org.slf4j.Logger;
|
import org.slf4j.Logger;
|
||||||
|
|
||||||
@Mixin(RSAbstractArchive.class)
|
@Mixin(RSAbstractArchive.class)
|
||||||
@@ -28,11 +24,11 @@ public abstract class RSAbstractArchiveMixin implements RSAbstractArchive
|
|||||||
@Shadow("client")
|
@Shadow("client")
|
||||||
private static RSClient client;
|
private static RSClient client;
|
||||||
|
|
||||||
@Inject
|
@Shadow("customClientScripts")
|
||||||
private boolean overlayOutdated;
|
private static Map<Integer, byte[]> customClientScripts;
|
||||||
|
|
||||||
@Inject
|
@Inject
|
||||||
private Map<String, String> scriptNames;
|
private boolean overlayOutdated;
|
||||||
|
|
||||||
@Inject
|
@Inject
|
||||||
@Override
|
@Override
|
||||||
@@ -54,34 +50,6 @@ public abstract class RSAbstractArchiveMixin implements RSAbstractArchive
|
|||||||
return rsData;
|
return rsData;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (scriptNames == null)
|
|
||||||
try
|
|
||||||
{
|
|
||||||
scriptNames = new HashMap<>();
|
|
||||||
InputStream is = ClassLoader.getSystemClassLoader().getResourceAsStream("scripts/");
|
|
||||||
if (is != null)
|
|
||||||
{
|
|
||||||
List<String> files = IOUtils.readLines(is, Charsets.UTF_8);
|
|
||||||
for (String s : files)
|
|
||||||
{
|
|
||||||
if (s.endsWith(".rs2asm"))
|
|
||||||
continue;
|
|
||||||
|
|
||||||
String scriptName = s.replace(".hash", "");
|
|
||||||
InputStream hashStream = ClassLoader.getSystemClassLoader().getResourceAsStream("scripts/" + scriptName + ".hash");
|
|
||||||
if (hashStream != null)
|
|
||||||
{
|
|
||||||
String scriptHash = (String) IOUtils.readLines(hashStream, Charsets.UTF_8).toArray()[0];
|
|
||||||
scriptNames.put(scriptHash, scriptName);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (IOException e)
|
|
||||||
{
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
|
|
||||||
final Logger log = client.getLogger();
|
final Logger log = client.getLogger();
|
||||||
final String path = String.format("/runelite/%s/%s", archiveId, groupId);
|
final String path = String.format("/runelite/%s/%s", archiveId, groupId);
|
||||||
|
|
||||||
@@ -105,12 +73,16 @@ public abstract class RSAbstractArchiveMixin implements RSAbstractArchive
|
|||||||
if (!overlayHash.equalsIgnoreCase(originalHash))
|
if (!overlayHash.equalsIgnoreCase(originalHash))
|
||||||
{
|
{
|
||||||
log.error("Script " + groupId + " is invalid, and will not be overlaid. This will break plugin(s)!");
|
log.error("Script " + groupId + " is invalid, and will not be overlaid. This will break plugin(s)!");
|
||||||
client.setOutdatedScript(scriptNames.get(overlayHash));
|
|
||||||
overlayOutdated = true;
|
overlayOutdated = true;
|
||||||
return rsData;
|
return rsData;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (customClientScripts.containsKey(archiveId << 16 | groupId))
|
||||||
|
{
|
||||||
|
return customClientScripts.get(archiveId << 16 | groupId);
|
||||||
|
}
|
||||||
|
|
||||||
try (final InputStream ovlIn = getClass().getResourceAsStream(path))
|
try (final InputStream ovlIn = getClass().getResourceAsStream(path))
|
||||||
{
|
{
|
||||||
return ByteStreams.toByteArray(ovlIn);
|
return ByteStreams.toByteArray(ovlIn);
|
||||||
|
|||||||
@@ -33,6 +33,7 @@ import java.util.ArrayList;
|
|||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import java.util.EnumSet;
|
import java.util.EnumSet;
|
||||||
|
import java.util.HashMap;
|
||||||
import java.util.HashSet;
|
import java.util.HashSet;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
@@ -132,6 +133,7 @@ import net.runelite.api.mixins.MethodHook;
|
|||||||
import net.runelite.api.mixins.Mixin;
|
import net.runelite.api.mixins.Mixin;
|
||||||
import net.runelite.api.mixins.Replace;
|
import net.runelite.api.mixins.Replace;
|
||||||
import net.runelite.api.mixins.Shadow;
|
import net.runelite.api.mixins.Shadow;
|
||||||
|
import net.runelite.api.overlay.OverlayIndex;
|
||||||
import net.runelite.api.vars.AccountType;
|
import net.runelite.api.vars.AccountType;
|
||||||
import net.runelite.api.widgets.Widget;
|
import net.runelite.api.widgets.Widget;
|
||||||
import net.runelite.api.widgets.WidgetConfig;
|
import net.runelite.api.widgets.WidgetConfig;
|
||||||
@@ -315,6 +317,9 @@ public abstract class RSClientMixin implements RSClient
|
|||||||
@Inject
|
@Inject
|
||||||
private static int tmpMenuOptionsCount;
|
private static int tmpMenuOptionsCount;
|
||||||
|
|
||||||
|
@Inject
|
||||||
|
private static final Map<Integer, byte[]> customClientScripts = new HashMap<>();
|
||||||
|
|
||||||
@Inject
|
@Inject
|
||||||
@Override
|
@Override
|
||||||
public void setPrintMenuActions(boolean yes)
|
public void setPrintMenuActions(boolean yes)
|
||||||
@@ -3055,5 +3060,37 @@ public abstract class RSClientMixin implements RSClient
|
|||||||
|
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Inject
|
||||||
|
@Override
|
||||||
|
public int addClientScript(byte[] script)
|
||||||
|
{
|
||||||
|
assert this.isClientThread() : "addClientScript must be called on client thread";
|
||||||
|
|
||||||
|
int highestUsedScript = -1;
|
||||||
|
for (int index : OverlayIndex.getOverlays())
|
||||||
|
{
|
||||||
|
if ((index >> 16) != 12)
|
||||||
|
{
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
int scriptId = index & 0xFFFF;
|
||||||
|
if (scriptId > highestUsedScript)
|
||||||
|
{
|
||||||
|
highestUsedScript = scriptId;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (highestUsedScript == -1)
|
||||||
|
{
|
||||||
|
highestUsedScript = 10000;
|
||||||
|
}
|
||||||
|
|
||||||
|
int newScriptId = highestUsedScript + 1;
|
||||||
|
OverlayIndex.getOverlays().add((12 << 16) | newScriptId);
|
||||||
|
customClientScripts.put((12 << 16) | newScriptId, script);
|
||||||
|
return newScriptId;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user