Wsamiaw · Scripting

Scripting

Wsamiaw embeds a JavaScript engine (Rhino). Each *.js file under config/Wsa/scripts/ runs at boot, listens to engine events, and can register its own ClickGUI modules with settings, keybinds, Cloud/Local sync, render drawing and packets.

Trust boundary. Scripts are not fully sandboxed — they can send packets and toggle modules. Only run code you wrote or fully trust.

Folder & Cloud / Local

config/Wsa/scripts/YourScript.js

In-game: Cloud tab → Scripts → Cloud / Local toggle, or chat with .script.

TabWhat it does
CloudBrowse community scripts. Apply runs + saves locally. Del removes your uploads. Download counts on cards.
LocalFiles on disk. Apply loads and runs. Del removes the file.

Quick start

  1. Create config/Wsa/scripts/hello.js (see below)
  2. In-game: .script reload — loads all scripts
  3. ClickGUI → your module appears under its category → enable hello
var m = modules.register({
  name: "HelloMod",
  category: "Misc",
  description: "Says hi",
  settings: [
    {name: "Range", type: "number", value: 3.0, min: 1.0, max: 6.0}
  ],
  onEnable: function() { chat("HelloMod on"); },
  onDisable: function() { chat("HelloMod off"); },
  onTick: function(e) {
    var aura = client.mod("KillAura");
    if (aura !== null && aura.isEnabled()) {
      chat("aura is on, range " + m.settingNum("Range"));
    }
  }
});

Script modules

modules.register(desc) creates a real cheat module: it shows in ClickGUI, HUD/ArrayList, keybinds and configs. Returns the module object.

FieldTypeNotes
namestring, requiredShown in ClickGUI/HUD
categorystringCombat / Movement / Render / Player / Misc / Settings (default Misc)
descriptionstringTooltip text
bindintKeycode, 0 = none
settingsarraySee setting types below
onEnable / onDisablefunctionToggle callbacks
onTick / onUpdate / onPacket / onRender2D / onRender3Dfunction(e)Only while the module is enabled

Runtime: m.settingNum(name), m.settingBool(name), m.settingStr(name), m.setSetting(name, value), m.isEnabled(), m.setEnabled(b). modules.list() returns names, modules.get(name) returns the module. Note: always use the typed getters (settingNum etc.) — plain setting() returns a Java wrapper. Same rule everywhere: compare Java values with == / != (or String(x)), never === / !== — plain setting() returns a Java wrapper.

Setting types

typeFieldsExample
boolvalue{name:"Fast", type:"bool", value:true}
numbervalue, min, max{name:"Range", type:"number", value:3.0, min:1.0, max:6.0}
intvalue, min, max{name:"Count", type:"int", value:2, min:0, max:10}
modevalue, options[]{name:"Mode", type:"mode", value:0, options:["A","B"]}
colorvalue (ARGB int){name:"Tint", type:"color", value:0xFF7C5CFF}
textvalue{name:"Label", type:"text", value:"hi"}

Event hooks

Global listeners (run regardless of modules): events.on(name, fn) with update, tick, packet, render2d, render3d.

Evente.getType()Useful members
updatePRE / POSTgetYaw/getPitch/getNewYaw/getNewPitch, setRotation(yaw,pitch,prio)
tickPRE / POSTPer-tick logic, timers
packetSEND / RECEIVEgetPacket(), setCancelled(true)
render2d—HUD drawing via render.*
render3d—World-space drawing, getPartialTicks()
events.on("packet", function(e) {
  if (e.getType().toString() === "RECEIVE") {
    var p = e.getPacket();
    if (p instanceof Packages.net.minecraft.network.play.server.S02PacketChat) {
      chat("chat packet seen");
    }
  }
});

Globals

NameWhat it is
mcMinecraft instance — mc.thePlayer, mc.theWorld, mc.gameSettings, …
chat(msg)Send a chat message
client.print(msg)Print to chat (local only)
client.mod(name)Built-in module (isEnabled(), setEnabled(b)) or null
client.getScriptName()This script's file name
modules.register(desc) / modules.get(name) / modules.list()Script modules (see above)
events.on(name, fn)Global hooks: update, tick, packet, render2d, render3d
Packages.*Full Java access, e.g. new Packages.net.minecraft.network.play.client.C01PacketChatMessage("hi")

render API

Call only during render2d / render3d. Colors are ARGB integers.

MethodNotes
render.rect(x1,y1,x2,y2,color)Filled rectangle
render.rounded(x,y,w,h,radius,color)Rounded rectangle
render.text(s,x,y,color)Vanilla font with shadow
render.textNoShadow(s,x,y,color)Vanilla font, no shadow
render.centerText(s,cx,y,color)Horizontally centered text
render.textWidth(s)Pixel width for layout
render.pill(x,y,w,h,bg,accent,text,textColor)ArrayList-style pill row with accent bar
render.image(path,x,y,w,h)Draw classpath/resource image, e.g. assets/wsamiaw/logo.png
render.push(x,y,scale,rotationDeg) / render.pop()Transform stack for custom animations (scale + rotate around point)
render.screenWidth() / render.screenHeight()Scaled screen size for HUD layout
render.time(), render.sin(v), render.cos(v)Animation helpers (seconds, trig)

Custom HUD element

var hud = modules.register({
  name: "MyHud", category: "Render",
  settings: [
    {name: "Scale", type: "number", value: 1.0, min: 0.5, max: 2.0}
  ],
  onRender2D: function(e) {
    var s = hud.settingNum("Scale");
    var w = 120 * s, h = 18 * s;
    var x = render.screenWidth() - w - 6, y = 40;
    var a = 0.5 + 0.5 * render.sin(render.time() * 2.0);
    var bg = 0xB0101014, accent = 0xFF7C5CFF;
    render.pill(x, y, w, h, bg, accent, "MyHud " + Math.round(a * 100), 0xFFFFFFFF);
  }
});

Packets

Inspect/cancel via the packet event; send via mc + Packages:

events.on("packet", function(e) {
  var p = e.getPacket();
  if (p instanceof Packages.net.minecraft.network.play.server.S02PacketChat) {
    var text = p.getChatComponent().getUnformattedText();
    if (text.indexOf("Victory") !== -1) chat("gg");
  }
});
var C01 = Packages.net.minecraft.network.play.client.C01PacketChatMessage;
mc.getNetHandler().addToSendQueue(new C01("hello"));
mc.getNetHandler().addToSendQueue(
  new Packages.net.minecraft.network.play.client.C03PacketPlayer(true));

Serverbound: C01 chat, C02 use entity, C03 player, C07 dig, C08 place, C09 held item, C0A swing, C0B action, C0D close, C0E click, C0F transaction, C10 creative, C13 abilities, C16 status. Clientbound: S02 chat, S04 equipment, S06 health, S08 pos look, S12 velocity, S13 destroy, S14 rel move, S18 teleport, S23 block change, S27 explosion, S29 sound, S2A particles, S45 title, S48 resource pack, …

Commands

CommandAction
.script listLoaded scripts + ON/OFF
.script reloadReload all scripts
.script load <name>Load one file
.script unload <name>Unload (removes its modules)
.script eval <js...>Run a snippet immediately

Aliases: .scripts, .js

Security

Trust boundary. Scripts are not sandboxed — through Packages they can touch any Java/Minecraft API, send packets and toggle modules. Only run code you wrote or fully trust. A throwing script reports to chat and keeps running; unload it with .script unload.

Examples

AutoGG

events.on("packet", function(e) {
  if (e.getType().toString() !== "RECEIVE") return;
  var p = e.getPacket();
  var S02 = Packages.net.minecraft.network.play.server.S02PacketChat;
  if (p instanceof S02) {
    if (p.getChatComponent().getUnformattedText().indexOf("Victory") !== -1) chat("gg");
  }
});

Toggle HUD

var m = modules.register({
  name: "HudToggle", category: "Render",
  onEnable: function() { client.mod("HUD").setEnabled(true); },
  onDisable: function() { client.mod("HUD").setEnabled(false); }
});

Aim readout

events.on("render2d", function(e) {
  var p = mc.thePlayer;
  if (p !== null) render.text("yaw " + p.rotationYaw.toFixed(1), 4, 4, 0xFFFFFFFF);
});

Download full reference: scripting-reference.html (markdown, copy/download)