# phBot xControl commands: run a whole party of bots from in-game chat

xControl is a phBot plugin that turns chat into a remote control. You run it on every bot in a party, add one or more leader names to its list, and from then on any message a leader sends that matches a command is carried out by every bot that hears it. Type `START` in party chat and the whole party starts botting. Whisper `FOLLOW` to one character and only that one follows you.

It is one of the [ten phBot plugins I maintain](https://www.mohamedgado.com/projects/phbot-plugins). The original was written by JellyBitz; my version adds commands, walk-script commands and a new tab. Every argument and default below is read from the source of xControl 1.9.1, not from memory.

## How do I set up xControl?

1. Download `xControl.py` from the [plugin repo](https://github.com/Vette1123/phbot-plugins) and put it in the `Plugins` folder inside your phBot folder.
2. Restart phBot. The plugin gets its own tab, named xControl.
3. On each bot, type the leader's character name into the box under **Party Leaders** and press **Add**. The list is saved per character, so you do this once.
4. Log the leader in and type a command in chat.

Three rules decide whether a command runs:

- **Only leaders are obeyed.** A message from anyone not on that bot's leader list is ignored, whoever sends it.
- **Commands are uppercase.** The plugin compares text exactly, so `START` works and `start` does nothing.
- **The chat channel picks who reacts.** Party chat reaches every bot in the party. A private message reaches one bot. All chat reaches every bot close enough to see it.

Arguments are separated by spaces. Below, `<name>` is required and `[name]` is optional.

## Which commands start, stop and move the bots?

| Command | What it does |
| --- | --- |
| `START` | Starts botting. |
| `STOP` | Stops botting. |
| `TRACE [player]` | Starts phBot's trace on a player. With no name it traces whoever sent the command. |
| `NOTRACE` | Stops tracing. |
| `FOLLOW [player] [distance]` | Follows a player at a distance. Defaults: the sender, at 10. `FOLLOW 5` follows you at 5; `FOLLOW Gado 3` follows Gado at 3. |
| `NOFOLLOW` | Stops following. |
| `MOVEON [radius]` | Walks to a random point within the radius, default 10. Handy for unsticking a bot. |
| `SIT` | Sits down or stands up. |
| `JUMP` | Plays the jump emote. |
| `DC` | Disconnects the bot. |

## How do I change where the bots train?

| Command | What it does |
| --- | --- |
| `SETPOS` | Sets the training position to where the bot stands now. |
| `SETPOS <x> <y> [region] [z]` | Sets the training position to those coordinates. |
| `GETPOS` | The bot whispers its X, Y, Z and region back to you. Use it before `SETPOS` with coordinates. |
| `SETRADIUS [radius]` | Sets the training radius. With no number it resets to 35. A negative number is made positive. |
| `SETAREA <name>` | Switches to a training area you saved in phBot, by name. |
| `SETSCRIPT [path]` | Sets the training walk script. With no path it clears the script. |
| `PROFILE [name]` | Loads a phBot profile. With no name it loads `Default`. |

## How do I teleport, return or revive the party?

| Command | What it does |
| --- | --- |
| `TP <source> <destination>` | Teleports through a teleporter, naming both ends. Separate them with a space or a comma. |
| `TP <destination>` | Looks for a nearby teleporter NPC that goes there and uses it. |
| `RETURN` | Uses a return scroll after a random 0.5 to 2 second delay, so the party does not leave in the same tick. A dead bot revives at its return point instead. |
| `RECALL <npc>` | Sets the return point at a town NPC standing nearby. |
| `R <player>` | Uses a reverse return scroll to that player. |
| `REVERSE return` | Reverse return scroll to the last return point. |
| `REVERSE death` | Reverse return scroll to where the bot last died. |
| `REVERSE player <name>` | Reverse return scroll to a player. Same as `R`. |
| `REVERSE zone <name>` | Reverse return scroll to a zone. |

## Which commands help in PvP and job runs?

| Command | What it does |
| --- | --- |
| `ZERK` | Activates Berserk. |
| `CAPE [color]` | Puts on a PvP cape: `red`, `gray`, `blue`, `white` or `yellow`. `CAPE off` removes it. With no colour it picks yellow. |
| `EQUIP <item>` | Equips an item from the inventory whose name contains the text, ignoring case. `trader`, `hunter`, `thief` and `job` pick the matching job suit. |
| `UNEQUIP <item>` | Takes an equipped item off, matched the same way. `UNEQUIP job` removes the job suit. |
| `MOUNT [pet]` | Mounts a horse, or a summoned pet of that phBot pet type. Default: horse. |
| `DISMOUNT [pet]` | Dismounts, same defaults. |
| `TERMINATE` | Dismisses the summoned pet. |

`EQUIP trader` followed by `START` on a caravan party is the whole job-suit swap in two messages.

## What about items, party and chat?

| Command | What it does |
| --- | --- |
| `USE <item>` | Uses an inventory item whose name contains the text. Unlike `EQUIP`, this match is case-sensitive, so type the name as the game spells it. |
| `SORT` | Sorts the inventory. |
| `GETOUT` | Leaves the party, if the bot is in one. |
| `CHAT <type> <message>` | Makes the bot speak. Types: `all`, `party`, `guild`, `union`, `stall`, `global`. |
| `CHAT private <player> <message>` | Sends a private message from the bot. `note` takes a player the same way and sends a note. |
| `INJECT <opcode> [true\|false] <bytes...>` | Sends a raw packet to the server: the opcode in hex, an optional "encrypted" flag, then the data bytes in hex. For people who know the packet they want; [xPacketTool](https://www.mohamedgado.com/projects/phbot-plugins) is the safer way to find one. |

## Can xControl run from a walk script?

Yes. xControl adds five commands that phBot walk scripts (`.txt`) can call. They use commas, like every script command:

| Script command | What it does |
| --- | --- |
| `chat,<type>,<message>` | Sends chat. `chat,private,<name>,<message>` and `chat,note,<name>,<message>` take a player name first. |
| `pinvite,<name>[,<name>...]` | Invites each named player standing nearby to the party, creating the party if there is none. |
| `wait_party,<count>[,<timeout ms>]` | Pauses the script until the party has at least that many members. The timeout defaults to 60 seconds. |
| `use_scroll,<keyword>` | Uses the first item whose name contains the keyword, ignoring case. If it is in a grab pet, it moves it to the inventory first. Example: `use_scroll,Random Awaken`. |
| `leaveparty` | Leaves the party, like `GETOUT`. |

A script that gathers a party before a run looks like this:

```text
pinvite,Alpha,Bravo,Charlie
wait_party,4,90000
chat,party,START
```

The bot that runs it sends `START` in party chat, and every party bot with that character in its leader list starts.

## Why does a command do nothing?

Check these in order:

- **The sender is not on that bot's leader list.** The list belongs to each bot. Adding the leader on one character does not add it on the others.
- **The command was typed in lowercase,** or with extra text before it. The message has to start with the command.
- **The bot cannot hear the channel.** A private message reaches one bot. Party chat only reaches bots in your party.
- **The item or NPC name does not match.** `EQUIP` and `USE` search by part of the name; `RECALL` and `TP <destination>` need the NPC near the bot.

The phBot log shows a line for most commands, including the failures (`Plugin: ...`), so read it first. If you are writing your own plugin on top of this, the [phBot Python API guide](https://www.mohamedgado.com/writing/phbot-plugin-python-api) covers the `handle_chat` hook xControl is built on.

