project: Injector and mixins

This commit is contained in:
Owain van Brakel
2021-12-15 05:39:57 +01:00
parent 62a5942180
commit 6b133497df
30 changed files with 530 additions and 168 deletions

View File

@@ -13,6 +13,7 @@ import static com.openosrs.injector.rsapi.RSApi.RL_API_BASE;
import com.openosrs.injector.rsapi.RSApiClass; import com.openosrs.injector.rsapi.RSApiClass;
import com.openosrs.injector.rsapi.RSApiMethod; import com.openosrs.injector.rsapi.RSApiMethod;
import java.util.List; import java.util.List;
import java.util.Set;
import java.util.function.Consumer; import java.util.function.Consumer;
import java.util.function.Predicate; import java.util.function.Predicate;
import java.util.stream.Collectors; import java.util.stream.Collectors;
@@ -340,6 +341,11 @@ public interface InjectUtil
} }
static Type apiToDeob(InjectData data, Type api) static Type apiToDeob(InjectData data, Type api)
{
return apiToDeob(data, api, null);
}
static Type apiToDeob(InjectData data, Type api, Type deobType)
{ {
if (api.isPrimitive()) if (api.isPrimitive())
{ {
@@ -354,29 +360,43 @@ public interface InjectUtil
else if (internalName.startsWith(RL_API_BASE)) else if (internalName.startsWith(RL_API_BASE))
{ {
Class rlApiC = new Class(internalName); Class rlApiC = new Class(internalName);
RSApiClass highestKnown = data.getRsApi().withInterface(rlApiC); Set<RSApiClass> allClasses = data.getRsApi().withInterface(rlApiC);
// Cheeky unchecked exception // Cheeky unchecked exception
assert highestKnown != null : "No rs api class implements rl api class " + rlApiC.toString(); assert allClasses.size() > 0 : "No rs api class implements rl api class " + rlApiC.toString();
boolean changed; if (allClasses.size() == 1)
do
{ {
changed = false; RSApiClass highestKnown = allClasses.stream().findFirst().get();
boolean changed;
for (RSApiClass interf : highestKnown.getApiInterfaces()) do
{ {
if (interf.getInterfaces().contains(rlApiC)) changed = false;
for (RSApiClass interf : highestKnown.getApiInterfaces())
{ {
highestKnown = interf; if (interf.getInterfaces().contains(rlApiC))
changed = true; {
break; highestKnown = interf;
changed = true;
break;
}
}
}
while (changed);
return apiToDeob(data, Type.getType(highestKnown.getName(), api.getDimensions()));
}
else
{
for (RSApiClass rsApiClass : allClasses)
{
if (rsApiClass.getName().contains(deobType.getInternalName()))
{
return apiToDeob(data, Type.getType(rsApiClass.getName(), api.getDimensions()));
} }
} }
} }
while (changed);
return apiToDeob(data, Type.getType(highestKnown.getName(), api.getDimensions()));
} }
return api; return api;

View File

@@ -23,7 +23,7 @@ import com.openosrs.injector.injectors.raw.Occluder;
import com.openosrs.injector.injectors.raw.RasterizerAlpha; import com.openosrs.injector.injectors.raw.RasterizerAlpha;
import com.openosrs.injector.injectors.raw.RenderDraw; import com.openosrs.injector.injectors.raw.RenderDraw;
import com.openosrs.injector.injectors.raw.CopyRuneLiteClasses; import com.openosrs.injector.injectors.raw.CopyRuneLiteClasses;
import com.openosrs.injector.injectors.raw.RuneLiteIterableHashTable; import com.openosrs.injector.injectors.raw.RuneLiteIterables;
import com.openosrs.injector.injectors.raw.RuneliteObject; import com.openosrs.injector.injectors.raw.RuneliteObject;
import com.openosrs.injector.injectors.raw.ScriptVM; import com.openosrs.injector.injectors.raw.ScriptVM;
import com.openosrs.injector.rsapi.RSApi; import com.openosrs.injector.rsapi.RSApi;
@@ -117,7 +117,7 @@ public class Injector extends InjectData implements InjectTaskHandler
inject(new CopyRuneLiteClasses(this)); inject(new CopyRuneLiteClasses(this));
inject(new RuneLiteIterableHashTable(this)); inject(new RuneLiteIterables(this));
inject(new RuneliteObject(this)); inject(new RuneliteObject(this));

View File

@@ -131,7 +131,7 @@ public class RSApiInjector extends AbstractInjector
} }
else if (sig.size() == 0) else if (sig.size() == 0)
{ {
Type type = InjectUtil.apiToDeob(inject, sig.getReturnValue()); Type type = InjectUtil.apiToDeob(inject, sig.getReturnValue(), deobType);
if (deobType.equals(type)) if (deobType.equals(type))
{ {
continue; continue;

View File

@@ -19,6 +19,7 @@ import net.runelite.asm.Type;
import net.runelite.asm.attributes.Code; import net.runelite.asm.attributes.Code;
import net.runelite.asm.attributes.code.Instruction; import net.runelite.asm.attributes.code.Instruction;
import net.runelite.asm.attributes.code.Instructions; import net.runelite.asm.attributes.code.Instructions;
import net.runelite.asm.attributes.code.instructions.CheckCast;
import net.runelite.asm.attributes.code.instructions.GetField; import net.runelite.asm.attributes.code.instructions.GetField;
import net.runelite.asm.attributes.code.instructions.GetStatic; import net.runelite.asm.attributes.code.instructions.GetStatic;
import net.runelite.asm.attributes.code.instructions.InvokeSpecial; import net.runelite.asm.attributes.code.instructions.InvokeSpecial;
@@ -35,7 +36,9 @@ public class CopyRuneLiteClasses extends AbstractInjector
{ {
private static final List<String> RUNELITE_OBJECTS = List.of( private static final List<String> RUNELITE_OBJECTS = List.of(
"RuneLiteObject", "RuneLiteObject",
"RuneLiteIterableHashTable" "RuneLiteIterableLinkDeque",
"RuneLiteIterableNodeDeque",
"RuneLiteIterableNodeHashTable"
); );
public CopyRuneLiteClasses(InjectData inject) public CopyRuneLiteClasses(InjectData inject)

View File

@@ -1,61 +0,0 @@
/*
* Copyright (c) 2021, Owain van Brakel <https://github.com/Owain94>
* All rights reserved.
*
* This code is licensed under GPL3, see the complete license in
* the LICENSE file in the root directory of this submodule.
*/
package com.openosrs.injector.injectors.raw;
import com.openosrs.injector.injection.InjectData;
import com.openosrs.injector.injectors.AbstractInjector;
import java.util.List;
import net.runelite.asm.ClassFile;
import net.runelite.asm.Method;
import net.runelite.asm.attributes.Code;
import net.runelite.asm.attributes.code.Instruction;
import net.runelite.asm.attributes.code.InstructionType;
import net.runelite.asm.attributes.code.Instructions;
import net.runelite.asm.attributes.code.instructions.ALoad;
import net.runelite.asm.attributes.code.instructions.Dup;
import net.runelite.asm.attributes.code.instructions.InvokeSpecial;
import net.runelite.asm.attributes.code.instructions.New;
import net.runelite.asm.attributes.code.instructions.Return;
import net.runelite.asm.signature.Signature;
public class RuneLiteIterableHashTable extends AbstractInjector
{
private static final String RUNELITE_ITERABLE_HASHTABLE = "RuneLiteIterableHashTable";
public RuneLiteIterableHashTable(InjectData inject)
{
super(inject);
}
public void inject()
{
ClassFile runeliteIterableHashTableVanilla = inject.vanilla.findClass(RUNELITE_ITERABLE_HASHTABLE);
final ClassFile nodeHashTableVanilla = inject.toVanilla(
inject.getDeobfuscated()
.findClass("NodeHashTable")
);
Method copy = new Method(nodeHashTableVanilla, "iterator", new Signature("()Ljava/util/Iterator;"));
copy.setPublic();
final Code code = new Code(copy);
code.setMaxStack(3);
copy.setCode(code);
nodeHashTableVanilla.addMethod(copy);
final Instructions instructions = code.getInstructions();
final List<Instruction> ins = instructions.getInstructions();
ins.add(new New(instructions, runeliteIterableHashTableVanilla.getPoolClass()));
ins.add(new Dup(instructions));
ins.add(new ALoad(instructions, 0));
ins.add(new InvokeSpecial(instructions, new net.runelite.asm.pool.Method(runeliteIterableHashTableVanilla.getPoolClass(), "<init>", new Signature("(L" + nodeHashTableVanilla.getName() + ";)V"))));
ins.add(new Return(instructions, InstructionType.ARETURN));
}
}

View File

@@ -0,0 +1,124 @@
/*
* Copyright (c) 2021, Owain van Brakel <https://github.com/Owain94>
* All rights reserved.
*
* This code is licensed under GPL3, see the complete license in
* the LICENSE file in the root directory of this submodule.
*/
package com.openosrs.injector.injectors.raw;
import com.openosrs.injector.injection.InjectData;
import com.openosrs.injector.injectors.AbstractInjector;
import java.util.List;
import net.runelite.asm.ClassFile;
import net.runelite.asm.Method;
import net.runelite.asm.attributes.Code;
import net.runelite.asm.attributes.code.Instruction;
import net.runelite.asm.attributes.code.InstructionType;
import net.runelite.asm.attributes.code.Instructions;
import net.runelite.asm.attributes.code.instructions.ALoad;
import net.runelite.asm.attributes.code.instructions.Dup;
import net.runelite.asm.attributes.code.instructions.InvokeSpecial;
import net.runelite.asm.attributes.code.instructions.New;
import net.runelite.asm.attributes.code.instructions.Return;
import net.runelite.asm.signature.Signature;
public class RuneLiteIterables extends AbstractInjector
{
private static final String RUNELITE_ITERABLE_HASHTABLE = "RuneLiteIterableNodeHashTable";
private static final String RUNELITE_ITERABLE_NODE_DEQUE = "RuneLiteIterableNodeDeque";
private static final String RUNELITE_ITERABLE_LINK_DEQUE = "RuneLiteIterableLinkDeque";
public RuneLiteIterables(InjectData inject)
{
super(inject);
}
public void inject()
{
injectHashTable();
injectNodeDeque();
injectLinkDeque();
}
public void injectHashTable()
{
ClassFile runeliteIterableHashTableVanilla = inject.vanilla.findClass(RUNELITE_ITERABLE_HASHTABLE);
final ClassFile nodeHashTableVanilla = inject.toVanilla(
inject.getDeobfuscated()
.findClass(RUNELITE_ITERABLE_HASHTABLE.replace("RuneLiteIterable", ""))
);
Method copy = new Method(nodeHashTableVanilla, "iterator", new Signature("()Ljava/util/Iterator;"));
copy.setPublic();
final Code code = new Code(copy);
code.setMaxStack(3);
copy.setCode(code);
nodeHashTableVanilla.addMethod(copy);
final Instructions instructions = code.getInstructions();
final List<Instruction> ins = instructions.getInstructions();
ins.add(new New(instructions, runeliteIterableHashTableVanilla.getPoolClass()));
ins.add(new Dup(instructions));
ins.add(new ALoad(instructions, 0));
ins.add(new InvokeSpecial(instructions, new net.runelite.asm.pool.Method(runeliteIterableHashTableVanilla.getPoolClass(), "<init>", new Signature("(L" + nodeHashTableVanilla.getName() + ";)V"))));
ins.add(new Return(instructions, InstructionType.ARETURN));
}
public void injectNodeDeque()
{
ClassFile runeliteIterableNodeDequeVanilla = inject.vanilla.findClass(RUNELITE_ITERABLE_NODE_DEQUE);
final ClassFile nodeDequeVanilla = inject.toVanilla(
inject.getDeobfuscated()
.findClass(RUNELITE_ITERABLE_NODE_DEQUE.replace("RuneLiteIterable", ""))
);
Method copy = new Method(nodeDequeVanilla, "iterator", new Signature("()Ljava/util/Iterator;"));
copy.setPublic();
final Code code = new Code(copy);
code.setMaxStack(3);
copy.setCode(code);
nodeDequeVanilla.addMethod(copy);
final Instructions instructions = code.getInstructions();
final List<Instruction> ins = instructions.getInstructions();
ins.add(new New(instructions, runeliteIterableNodeDequeVanilla.getPoolClass()));
ins.add(new Dup(instructions));
ins.add(new ALoad(instructions, 0));
ins.add(new InvokeSpecial(instructions, new net.runelite.asm.pool.Method(runeliteIterableNodeDequeVanilla.getPoolClass(), "<init>", new Signature("(L" + nodeDequeVanilla.getName() + ";)V"))));
ins.add(new Return(instructions, InstructionType.ARETURN));
}
public void injectLinkDeque()
{
ClassFile runeliteIterableLinkDequeVanilla = inject.vanilla.findClass(RUNELITE_ITERABLE_LINK_DEQUE);
final ClassFile linkDequeVanilla = inject.toVanilla(
inject.getDeobfuscated()
.findClass(RUNELITE_ITERABLE_LINK_DEQUE.replace("RuneLiteIterable", ""))
);
Method copy = new Method(linkDequeVanilla, "iterator", new Signature("()Ljava/util/Iterator;"));
copy.setPublic();
final Code code = new Code(copy);
code.setMaxStack(3);
copy.setCode(code);
linkDequeVanilla.addMethod(copy);
final Instructions instructions = code.getInstructions();
final List<Instruction> ins = instructions.getInstructions();
ins.add(new New(instructions, runeliteIterableLinkDequeVanilla.getPoolClass()));
ins.add(new Dup(instructions));
ins.add(new ALoad(instructions, 0));
ins.add(new InvokeSpecial(instructions, new net.runelite.asm.pool.Method(runeliteIterableLinkDequeVanilla.getPoolClass(), "<init>", new Signature("(L" + linkDequeVanilla.getName() + ";)V"))));
ins.add(new Return(instructions, InstructionType.ARETURN));
}
}

View File

@@ -15,8 +15,10 @@ import java.io.FileInputStream;
import java.io.IOException; import java.io.IOException;
import java.io.InputStream; import java.io.InputStream;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.HashSet;
import java.util.Iterator; import java.util.Iterator;
import java.util.List; import java.util.List;
import java.util.Set;
import lombok.Getter; import lombok.Getter;
import lombok.NoArgsConstructor; import lombok.NoArgsConstructor;
import net.runelite.asm.Type; import net.runelite.asm.Type;
@@ -111,23 +113,19 @@ public class RSApi implements Iterable<RSApiClass>
return findClass(name) != null; return findClass(name) != null;
} }
public RSApiClass withInterface(Class interf) public Set<RSApiClass> withInterface(Class interf)
{ {
RSApiClass clazz = findClass(interf.getName()); Set<RSApiClass> classes = new HashSet<>();
if (clazz != null)
{
return clazz;
}
for (RSApiClass apiC : this) for (RSApiClass apiC : this)
{ {
if (apiC.getInterfaces().contains(interf)) if (apiC.getInterfaces().contains(interf))
{ {
return apiC; classes.add(apiC);
} }
} }
return null; return classes;
} }
@NotNull @NotNull

View File

@@ -59,15 +59,15 @@ public abstract class ClickboxMixin implements RSClient
// otherwise we must check if the mouse is in a triangle // otherwise we must check if the mouse is in a triangle
final int vertexCount = model.getVerticesCount(); final int vertexCount = model.getVerticesCount();
final int triangleCount = model.getTrianglesCount(); final int triangleCount = model.getFaceCount();
final int[] vertexX = model.getVerticesX(); final int[] vertexX = model.getVerticesX();
final int[] vertexY = model.getVerticesY(); final int[] vertexY = model.getVerticesY();
final int[] vertexZ = model.getVerticesZ(); final int[] vertexZ = model.getVerticesZ();
final int[] triangleX = model.getTrianglesX(); final int[] triangleX = model.getFaceIndices1();
final int[] triangleY = model.getTrianglesY(); final int[] triangleY = model.getFaceIndices2();
final int[] triangleZ = model.getTrianglesZ(); final int[] triangleZ = model.getFaceIndices3();
final int[] color3 = model.getFaceColors3(); final int[] color3 = model.getFaceColors3();

View File

@@ -39,9 +39,10 @@ import java.util.Map;
import java.util.Set; import java.util.Set;
import javax.annotation.Nonnull; import javax.annotation.Nonnull;
import javax.annotation.Nullable; import javax.annotation.Nullable;
import net.runelite.api.Animation;
import net.runelite.api.ChatMessageType; import net.runelite.api.ChatMessageType;
import net.runelite.api.EnumComposition; import net.runelite.api.EnumComposition;
import net.runelite.api.Friend; import net.runelite.api.FriendContainer;
import net.runelite.api.GameState; import net.runelite.api.GameState;
import net.runelite.api.GrandExchangeOffer; import net.runelite.api.GrandExchangeOffer;
import net.runelite.api.GraphicsObject; import net.runelite.api.GraphicsObject;
@@ -79,7 +80,6 @@ import net.runelite.api.Point;
import net.runelite.api.Prayer; import net.runelite.api.Prayer;
import net.runelite.api.Projectile; import net.runelite.api.Projectile;
import net.runelite.api.ScriptEvent; import net.runelite.api.ScriptEvent;
import net.runelite.api.Sequence;
import net.runelite.api.Skill; import net.runelite.api.Skill;
import net.runelite.api.SpritePixels; import net.runelite.api.SpritePixels;
import net.runelite.api.StructComposition; import net.runelite.api.StructComposition;
@@ -789,6 +789,15 @@ public abstract class RSClientMixin implements RSClient
setChatCycle(getCycleCntr()); setChatCycle(getCycleCntr());
} }
@Inject
@Override
public MenuEntry createMenuEntry(int idx)
{
// TODO: Implement this
return new MenuEntry();
}
@Inject @Inject
@Override @Override
public MenuEntry[] getMenuEntries() public MenuEntry[] getMenuEntries()
@@ -887,9 +896,9 @@ public abstract class RSClientMixin implements RSClient
options[oldCount] = event.getOption(); options[oldCount] = event.getOption();
targets[oldCount] = event.getTarget(); targets[oldCount] = event.getTarget();
identifiers[oldCount] = event.getIdentifier(); identifiers[oldCount] = event.getIdentifier();
opcodes[oldCount] = event.getOpcode(); opcodes[oldCount] = event.getType();
arguments1[oldCount] = event.getParam0(); arguments1[oldCount] = event.getActionParam0();
arguments2[oldCount] = event.getParam1(); arguments2[oldCount] = event.getActionParam1();
forceLeftClick[oldCount] = event.isForceLeftClick(); forceLeftClick[oldCount] = event.isForceLeftClick();
} }
} }
@@ -999,7 +1008,7 @@ public abstract class RSClientMixin implements RSClient
@Inject @Inject
@Override @Override
public NameableContainer<Friend> getFriendContainer() public FriendContainer getFriendContainer()
{ {
return getFriendManager().getFriendContainer(); return getFriendManager().getFriendContainer();
} }
@@ -2427,7 +2436,7 @@ public abstract class RSClientMixin implements RSClient
} }
@Inject @Inject
public Sequence loadAnimation(int id) public Animation loadAnimation(int id)
{ {
return client.getSequenceDefinition(id); return client.getSequenceDefinition(id);
} }

View File

@@ -0,0 +1,55 @@
/*
* Copyright (c) 2016-2017, Adam <Adam@sigterm.info>
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this
* list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright notice,
* this list of conditions and the following disclaimer in the documentation
* and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
package net.runelite.mixins;
import net.runelite.api.mixins.Inject;
import net.runelite.api.mixins.Mixin;
import net.runelite.rs.api.RSFriendLoginUpdate;
import net.runelite.rs.api.RSUsername;
@Mixin(RSFriendLoginUpdate.class)
public abstract class RSFriendLoginUpdatesMixin implements RSFriendLoginUpdate
{
@Inject
@Override
public String getName()
{
final RSUsername rsName = getRsName();
if (rsName == null)
{
return null;
}
String name = rsName.getName();
if (name == null)
{
return null;
}
return name.replace('\u00A0', ' ');
}
}

View File

@@ -0,0 +1,51 @@
/*
* Copyright (c) 2016-2017, Adam <Adam@sigterm.info>
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this
* list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright notice,
* this list of conditions and the following disclaimer in the documentation
* and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
package net.runelite.mixins;
import net.runelite.api.mixins.Inject;
import net.runelite.api.mixins.Mixin;
import net.runelite.rs.api.RSLink;
import net.runelite.rs.api.RSLinkDeque;
@Mixin(RSLinkDeque.class)
public abstract class RSLinkDequeMixin implements RSLinkDeque
{
@Inject
@Override
public void clear()
{
while (true)
{
RSLink rsLink = getSentinel().getPrevious();
if (rsLink == getSentinel())
{
setCurrent(null);
return;
}
rsLink.remove();
}
}
}

View File

@@ -78,7 +78,7 @@ public abstract class RSModelMixin implements RSModel
{ {
if (getFaceTextures() != null) if (getFaceTextures() != null)
{ {
int count = getTrianglesCount(); int count = getFaceCount();
float[] uv = new float[count * 6]; float[] uv = new float[count * 6];
int idx = 0; int idx = 0;
@@ -91,10 +91,10 @@ public abstract class RSModelMixin implements RSModel
if (modelUV != null) if (modelUV != null)
{ {
System.arraycopy(modelUV, 0, uv, idx, model.getTrianglesCount() * 6); System.arraycopy(modelUV, 0, uv, idx, model.getFaceCount() * 6);
} }
idx += model.getTrianglesCount() * 6; idx += model.getFaceCount() * 6;
} }
} }
@@ -131,14 +131,14 @@ public abstract class RSModelMixin implements RSModel
@Inject @Inject
public List<Triangle> getTriangles() public List<Triangle> getTriangles()
{ {
int[] trianglesX = getTrianglesX(); int[] trianglesX = getFaceIndices1();
int[] trianglesY = getTrianglesY(); int[] trianglesY = getFaceIndices2();
int[] trianglesZ = getTrianglesZ(); int[] trianglesZ = getFaceIndices3();
List<Vertex> vertices = getVertices(); List<Vertex> vertices = getVertices();
List<Triangle> triangles = new ArrayList<>(getTrianglesCount()); List<Triangle> triangles = new ArrayList<>(getFaceCount());
for (int i = 0; i < getTrianglesCount(); ++i) for (int i = 0; i < getFaceCount(); ++i)
{ {
int triangleX = trianglesX[i]; int triangleX = trianglesX[i];
int triangleY = trianglesY[i]; int triangleY = trianglesY[i];
@@ -408,14 +408,14 @@ public abstract class RSModelMixin implements RSModel
rl$vertexNormalsY = new int[verticesCount]; rl$vertexNormalsY = new int[verticesCount];
rl$vertexNormalsZ = new int[verticesCount]; rl$vertexNormalsZ = new int[verticesCount];
int[] trianglesX = getTrianglesX(); int[] trianglesX = getFaceIndices1();
int[] trianglesY = getTrianglesY(); int[] trianglesY = getFaceIndices2();
int[] trianglesZ = getTrianglesZ(); int[] trianglesZ = getFaceIndices3();
int[] verticesX = getVerticesX(); int[] verticesX = getVerticesX();
int[] verticesY = getVerticesY(); int[] verticesY = getVerticesY();
int[] verticesZ = getVerticesZ(); int[] verticesZ = getVerticesZ();
for (int i = 0; i < getTrianglesCount(); ++i) for (int i = 0; i < getFaceCount(); ++i)
{ {
int var9 = trianglesX[i]; int var9 = trianglesX[i];
int var10 = trianglesY[i]; int var10 = trianglesY[i];

View File

@@ -181,13 +181,13 @@ public abstract class RSPlayerMixin implements RSPlayer
final int tileHeight = Perspective.getTileHeight(client, new LocalPoint(localX, localY), client.getPlane()); final int tileHeight = Perspective.getTileHeight(client, new LocalPoint(localX, localY), client.getPlane());
Perspective.modelToCanvas(client, model.getVerticesCount(), localX, localY, tileHeight, getOrientation(), model.getVerticesX(), model.getVerticesZ(), model.getVerticesY(), x2d, y2d); Perspective.modelToCanvas(client, model.getVerticesCount(), localX, localY, tileHeight, getOrientation(), model.getVerticesX(), model.getVerticesZ(), model.getVerticesY(), x2d, y2d);
ArrayList polys = new ArrayList(model.getTrianglesCount()); ArrayList polys = new ArrayList(model.getFaceCount());
int[] trianglesX = model.getTrianglesX(); int[] trianglesX = model.getFaceIndices1();
int[] trianglesY = model.getTrianglesY(); int[] trianglesY = model.getFaceIndices2();
int[] trianglesZ = model.getTrianglesZ(); int[] trianglesZ = model.getFaceIndices3();
for (int triangle = 0; triangle < model.getTrianglesCount(); ++triangle) for (int triangle = 0; triangle < model.getFaceCount(); ++triangle)
{ {
int[] xx = int[] xx =
{ {

View File

@@ -24,9 +24,9 @@
*/ */
package net.runelite.mixins; package net.runelite.mixins;
import net.runelite.api.Animation;
import net.runelite.api.Model; import net.runelite.api.Model;
import net.runelite.api.Perspective; import net.runelite.api.Perspective;
import net.runelite.api.Sequence;
import net.runelite.api.coords.LocalPoint; import net.runelite.api.coords.LocalPoint;
import net.runelite.api.mixins.Inject; import net.runelite.api.mixins.Inject;
import net.runelite.api.mixins.Mixin; import net.runelite.api.mixins.Mixin;
@@ -55,7 +55,7 @@ public abstract class RuneLiteObjectMixin implements RSRuneLiteObject
} }
@Inject @Inject
public void setAnimation(Sequence var1) public void setAnimation(Animation var1)
{ {
setFrame(0); setFrame(0);
setFrameCycle(0); setFrameCycle(0);

View File

@@ -1,3 +1,13 @@
package net.runelite.rs.api; package net.runelite.rs.api;
public interface RSFriendLoginUpdate {} import net.runelite.api.PendingLogin;
import net.runelite.mapping.Import;
public interface RSFriendLoginUpdate extends PendingLogin
{
@Import("username")
RSUsername getRsName();
@Import("world")
short getWorld();
}

View File

@@ -1,11 +1,12 @@
package net.runelite.rs.api; package net.runelite.rs.api;
import net.runelite.api.FriendContainer;
import net.runelite.mapping.Import; import net.runelite.mapping.Import;
public interface RSFriendSystem public interface RSFriendSystem
{ {
@Import("friendsList") @Import("friendsList")
RSFriendsList getFriendContainer(); FriendContainer getFriendContainer();
@Import("ignoreList") @Import("ignoreList")
RSIgnoreList getIgnoreContainer(); RSIgnoreList getIgnoreContainer();

View File

@@ -1,6 +1,12 @@
package net.runelite.rs.api; package net.runelite.rs.api;
import net.runelite.api.Friend; import net.runelite.api.Deque;
import net.runelite.api.NameableContainer; import net.runelite.api.FriendContainer;
import net.runelite.api.PendingLogin;
import net.runelite.mapping.Import;
public interface RSFriendsList extends NameableContainer<Friend> {} public interface RSFriendsList extends FriendContainer
{
@Import("friendLoginUpdates")
Deque<PendingLogin> getPendingLogins();
}

View File

@@ -1,3 +1,15 @@
package net.runelite.rs.api; package net.runelite.rs.api;
public interface RSLink {} import net.runelite.mapping.Import;
public interface RSLink
{
@Import("previous")
RSLink getPrevious();
@Import("next")
RSLink next();
@Import("remove")
void remove();
}

View File

@@ -1,3 +1,25 @@
package net.runelite.rs.api; package net.runelite.rs.api;
public interface RSLinkDeque {} import net.runelite.api.Deque;
import net.runelite.mapping.Import;
public interface RSLinkDeque extends Deque
{
@Import("current")
RSLink getCurrent();
@Import("current")
void setCurrent(RSLink link);
@Import("sentinel")
RSLink getSentinel();
@Import("last")
RSLink last();
@Import("previous")
RSLink previous();
@Import("addFirst")
void addFirst(RSLink val);
}

View File

@@ -48,19 +48,19 @@ public interface RSModel extends RSRenderable, Model
@Import("indicesCount") @Import("indicesCount")
@Override @Override
int getTrianglesCount(); int getFaceCount();
@Import("indices1") @Import("indices1")
@Override @Override
int[] getTrianglesX(); int[] getFaceIndices1();
@Import("indices2") @Import("indices2")
@Override @Override
int[] getTrianglesY(); int[] getFaceIndices2();
@Import("indices3") @Import("indices3")
@Override @Override
int[] getTrianglesZ(); int[] getFaceIndices3();
@Import("faceColors1") @Import("faceColors1")
@Override @Override
@@ -76,7 +76,7 @@ public interface RSModel extends RSRenderable, Model
@Import("faceAlphas") @Import("faceAlphas")
@Override @Override
byte[] getTriangleTransparencies(); byte[] getFaceTransparencies();
@Import("faceRenderPriorities") @Import("faceRenderPriorities")
@Override @Override
@@ -184,4 +184,20 @@ public interface RSModel extends RSRenderable, Model
int[] getVertexNormalsZ(); int[] getVertexNormalsZ();
void setVertexNormalsZ(int[] vertexNormalsZ); void setVertexNormalsZ(int[] vertexNormalsZ);
@Import("overrideAmount")
@Override
byte getOverrideAmount();
@Import("overrideHue")
@Override
byte getOverrideHue();
@Import("overrideSaturation")
@Override
byte getOverrideSaturation();
@Import("overrideLuminance")
@Override
byte getOverrideLuminance();
} }

View File

@@ -1,8 +1,9 @@
package net.runelite.rs.api; package net.runelite.rs.api;
import net.runelite.api.AmbientSoundEffect;
import net.runelite.mapping.Import; import net.runelite.mapping.Import;
public interface RSObjectSound public interface RSObjectSound extends AmbientSoundEffect
{ {
@Import("x") @Import("x")
int getX(); int getX();

View File

@@ -0,0 +1,4 @@
package net.runelite.rs.api;
public interface RSRuneLiteIterableLinkDeque
{}

View File

@@ -0,0 +1,4 @@
package net.runelite.rs.api;
public interface RSRuneLiteIterableNodeDeque
{}

View File

@@ -1,26 +1,11 @@
package net.runelite.rs.api; package net.runelite.rs.api;
import net.runelite.api.Sequence; import net.runelite.api.Animation;
import net.runelite.api.SequenceDefinition; import net.runelite.api.SequenceDefinition;
import net.runelite.mapping.Import; import net.runelite.mapping.Import;
public interface RSSequenceDefinition extends RSNode, SequenceDefinition, Sequence public interface RSSequenceDefinition extends RSNode, SequenceDefinition, Animation
{ {
// @Import("stretches")
// boolean getStretches();
//
// @Import("maxLoops")
// int getMaxLoops();
//
// @Import("precedenceAnimating") --- All unused
// int getPrecedenceAnimating();
//
// @Import("replyMode")
// int getReplyMode();
//
// @Import("interleaveLeave")
// int[] getInterleaveLeave();
@Import("frameCount") @Import("frameCount")
@Override @Override
int getFrameCount(); int getFrameCount();

View File

@@ -200,13 +200,17 @@ public class Model extends Renderable {
@Export("zMidOffset") @Export("zMidOffset")
int zMidOffset; int zMidOffset;
@ObfuscatedName("bo") @ObfuscatedName("bo")
public byte field2494; @Export("overrideHue")
public byte overrideHue;
@ObfuscatedName("bf") @ObfuscatedName("bf")
public byte field2495; @Export("overrideSaturation")
public byte overrideSaturation;
@ObfuscatedName("be") @ObfuscatedName("be")
public byte field2479; @Export("overrideLuminance")
public byte overrideLuminance;
@ObfuscatedName("ce") @ObfuscatedName("ce")
public byte field2474; @Export("overrideAmount")
public byte overrideAmount;
static { static {
Model_sharedSequenceModel = new Model(); Model_sharedSequenceModel = new Model();
@@ -574,7 +578,7 @@ public class Model extends Renderable {
var2.field2449 = this.field2449; var2.field2449 = this.field2449;
var2.isSingleTile = this.isSingleTile; var2.isSingleTile = this.isSingleTile;
var2.resetBounds(); var2.resetBounds();
var2.field2474 = 0; var2.overrideAmount = 0;
return var2; return var2;
} }
@@ -1569,10 +1573,10 @@ public class Model extends Renderable {
} }
} else if (this.faceColors3[var1] == -1) { } else if (this.faceColors3[var1] == -1) {
Rasterizer3D.method3856(modelViewportYs[var2], modelViewportYs[var3], modelViewportYs[var4], modelViewportXs[var2], modelViewportXs[var3], modelViewportXs[var4], Model_colorPalette[this.faceColors1[var1]]); Rasterizer3D.method3856(modelViewportYs[var2], modelViewportYs[var3], modelViewportYs[var4], modelViewportXs[var2], modelViewportXs[var3], modelViewportXs[var4], Model_colorPalette[this.faceColors1[var1]]);
} else if (this.field2474 > 0) { } else if (this.overrideAmount > 0) {
var5 = this.method4216(this.faceColors1[var1], this.field2494, this.field2495, this.field2479, this.field2474); var5 = this.method4216(this.faceColors1[var1], this.overrideHue, this.overrideSaturation, this.overrideLuminance, this.overrideAmount);
var6 = this.method4216(this.faceColors2[var1], this.field2494, this.field2495, this.field2479, this.field2474); var6 = this.method4216(this.faceColors2[var1], this.overrideHue, this.overrideSaturation, this.overrideLuminance, this.overrideAmount);
var7 = this.method4216(this.faceColors3[var1], this.field2494, this.field2495, this.field2479, this.field2474); var7 = this.method4216(this.faceColors3[var1], this.overrideHue, this.overrideSaturation, this.overrideLuminance, this.overrideAmount);
Rasterizer3D.method3854(modelViewportYs[var2], modelViewportYs[var3], modelViewportYs[var4], modelViewportXs[var2], modelViewportXs[var3], modelViewportXs[var4], var5, var6, var7); Rasterizer3D.method3854(modelViewportYs[var2], modelViewportYs[var3], modelViewportYs[var4], modelViewportXs[var2], modelViewportXs[var3], modelViewportXs[var4], var5, var6, var7);
} else { } else {
Rasterizer3D.method3854(modelViewportYs[var2], modelViewportYs[var3], modelViewportYs[var4], modelViewportXs[var2], modelViewportXs[var3], modelViewportXs[var4], this.faceColors1[var1], this.faceColors2[var1], this.faceColors3[var1]); Rasterizer3D.method3854(modelViewportYs[var2], modelViewportYs[var3], modelViewportYs[var4], modelViewportXs[var2], modelViewportXs[var3], modelViewportXs[var4], this.faceColors1[var1], this.faceColors2[var1], this.faceColors3[var1]);

View File

@@ -129,12 +129,12 @@ public final class NPC extends Actor {
} }
if (super.field1146 != 0 && Client.cycle >= super.field1141 && Client.cycle < super.field1140) { if (super.field1146 != 0 && Client.cycle >= super.field1141 && Client.cycle < super.field1140) {
var3.field2494 = super.field1143; var3.overrideHue = super.field1143;
var3.field2495 = super.field1144; var3.overrideSaturation = super.field1144;
var3.field2479 = super.field1095; var3.overrideLuminance = super.field1095;
var3.field2474 = super.field1146; var3.overrideAmount = super.field1146;
} else { } else {
var3.field2474 = 0; var3.overrideAmount = 0;
} }
return var3; return var3;

View File

@@ -381,12 +381,12 @@ public final class Player extends Actor {
var3.isSingleTile = true; var3.isSingleTile = true;
if (super.field1146 != 0 && Client.cycle >= super.field1141 && Client.cycle < super.field1140) { if (super.field1146 != 0 && Client.cycle >= super.field1141 && Client.cycle < super.field1140) {
var3.field2494 = super.field1143; var3.overrideHue = super.field1143;
var3.field2495 = super.field1144; var3.overrideSaturation = super.field1144;
var3.field2479 = super.field1095; var3.overrideLuminance = super.field1095;
var3.field2474 = super.field1146; var3.overrideAmount = super.field1146;
} else { } else {
var3.field2474 = 0; var3.overrideAmount = 0;
} }
return var3; return var3;

View File

@@ -0,0 +1,49 @@
import java.util.Iterator;
import java.util.NoSuchElementException;
public class RuneLiteIterableLinkDeque implements Iterator<Link>
{
public final LinkDeque linkDeque;
public Link link;
public RuneLiteIterableLinkDeque(LinkDeque linkDeque)
{
this.linkDeque = linkDeque;
this.link = this.linkDeque.sentinel.previous;
}
@Override
public boolean hasNext()
{
return this.link != this.linkDeque.sentinel;
}
@Override
public Link next()
{
if (this.link == this.linkDeque.sentinel)
{
throw new NoSuchElementException();
}
else
{
Link friendLoginUpdate = this.link;
this.link = this.link.previous;
return friendLoginUpdate;
}
}
public void remove()
{
Link link = this.link.next;
if (link == this.linkDeque.sentinel)
{
throw new IllegalStateException();
}
else
{
link.remove();
}
}
}

View File

@@ -0,0 +1,49 @@
import java.util.Iterator;
import java.util.NoSuchElementException;
public class RuneLiteIterableNodeDeque implements Iterator
{
public final NodeDeque nodeDeque;
public Node node;
public RuneLiteIterableNodeDeque(NodeDeque nodeDeque)
{
this.nodeDeque = nodeDeque;
this.node = this.nodeDeque.sentinel.previous;
}
@Override
public boolean hasNext()
{
return this.node != this.nodeDeque.sentinel;
}
@Override
public Node next()
{
if (this.node == this.nodeDeque.sentinel)
{
throw new NoSuchElementException();
}
else
{
Node node = this.node;
this.node = this.node.previous;
return node;
}
}
public void remove()
{
Node node = this.node.next;
if (node == this.nodeDeque.sentinel)
{
throw new IllegalStateException();
}
else
{
node.remove();
}
}
}

View File

@@ -1,13 +1,13 @@
import java.util.Iterator; import java.util.Iterator;
import java.util.NoSuchElementException; import java.util.NoSuchElementException;
public class RuneLiteIterableHashTable implements Iterator public class RuneLiteIterableNodeHashTable implements Iterator
{ {
public Node node; public Node node;
public final NodeHashTable nodeHashTable; public final NodeHashTable nodeHashTable;
public int it; public int it;
public RuneLiteIterableHashTable(NodeHashTable nodeHashTable) public RuneLiteIterableNodeHashTable(NodeHashTable nodeHashTable)
{ {
this.nodeHashTable = nodeHashTable; this.nodeHashTable = nodeHashTable;
} }