You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Create and manage virtual inventories in PocketMine-MP.
4
3
5
-
## Installation
6
-
You can get the compiled .phar file on poggit by clicking [here](https://poggit.pmmp.io/ci/Muqsit/InvMenu/~).
4
+
## Installation and setup
5
+
Download the compiled .phar file from [Poggit CI](https://poggit.pmmp.io/ci/Muqsit/InvMenu/~) and place it in your `virions/` folder.
6
+
Read [installation](https://github.com/Muqsit/InvMenu/wiki/Installation) and [using in a plugin](https://github.com/Muqsit/InvMenu/wiki/Using-InvMenu-in-a-plugin)
7
+
for a more elaborate guide on how to setup InvMenu library.
7
8
8
-
## Usage
9
-
InvMenu supports creating a GUI out of any kind of `Inventory`.
9
+
> [!NOTE]
10
+
> You must register `InvMenuHandler` before you can use InvMenu.
11
+
> ```php
12
+
> // in class MyPlugin extends PluginBase:
13
+
> protected function onEnable() : void{
14
+
> if(!InvMenuHandler::isRegistered()){
15
+
> InvMenuHandler::register($this);
16
+
> }
17
+
> }
10
18
11
-
**NOTE:** You MUST register `InvMenuHandler` during plugin enable before you can begin creating `InvMenu` instances.
12
-
```php
13
-
if(!InvMenuHandler::isRegistered()){
14
-
InvMenuHandler::register($this);
15
-
}
16
-
```
19
+
## Create a virtual inventory
20
+
Quick start, use `InvMenu::create(InvMenu::TYPE_CHEST)->send($player);` to display a virtual chest inventory to a player.
17
21
18
-
## Creating an InvMenu instance
19
-
`InvMenu::create($identifier)` creates a new instance of InvMenu. `$identifier` must be an identifier of a registered `InvMenuType` object. InvMenu comes with 3 pre-registered `InvMenuType` identifiers: `InvMenu::TYPE_CHEST`, `InvMenu::TYPE_DOUBLE_CHEST` and `InvMenu::TYPE_HOPPER`.
22
+
`InvMenu::create($identifier)` creates an InvMenu instance. `$identifier` may be an identifier of a registered `InvMenuType` object.
23
+
InvMenu comes with 3 pre-registered inventory types of different sizes:
24
+
- `InvMenu::TYPE_CHEST` - a 27-slot normal chest inventory
25
+
- `InvMenu::TYPE_DOUBLE_CHEST` - a 54-slot double chest inventory
26
+
- `InvMenu::TYPE_HOPPER` - a 5-slot hopper inventory
20
27
21
28
```php
22
29
$menu = InvMenu::create(InvMenu::TYPE_CHEST);
23
-
```
24
-
25
-
To access this menu's inventory, you can use:
26
-
```php
27
30
$inventory = $menu->getInventory();
28
31
```
29
32
30
-
The`$inventory` implements pocketmine's `Inventory` interface, so you can access all the fancy pocketmine inventory methods.
33
+
As`$inventory` implements [PocketMine's Inventory interface](https://github.com/pmmp/PocketMine-MP/blob/stable/src/inventory/Inventory.php), you get to access all the fancy PocketMine inventory methods.
> One `InvMenu` can be sent to multiple players—even 2 players in different worlds, so everyone views and edits the same inventory as if it were one chest.
45
49
46
-
## Specifying a custom name to the menu
47
-
To set a custom name to a menu, use
48
-
```php
49
-
$menu->setName("Custom Name");
50
-
```
51
-
You can also specify a different menu name for each player separately during `InvMenu::send()`.
50
+
51
+
## Set a custom name
52
+
There are two ways to name an InvMenu. You can either specify a global name (see method A), or you can set a name at the time you send the menu (see method B).
$menu->send($player, "Greetings, " . $player->getName()); // method B
55
56
```
56
57
57
-
## Verifying whether the menu was sent to the player
58
-
Not a common occurrence but it's possible for plugins to disallow players from opening inventories.
59
-
This can also occur as an attempt to drop garbage `InvMenu::send()` requests (if you send two menus simultaneously without any delay in betweeen, the first menu request may be regarded as garbage).
58
+
## Verify whether a menu is sent successfully
59
+
`InvMenu::send()` is not guaranteed to succeed. A failure may arise from plugins cancelling InventoryOpenEvent, a disconnected player, or the player refusing the request (e.g., because they are in pause menu).
60
+
Use the `$callback` parameter to verify whether a menu has been opened.
To handle item transactions happening to and from the menu's inventory, you may specify a `Closure` handler that gets triggered by `InvMenu` every time a transaction occurs. You may allow, cancel and do other things within this handler. To register a transaction handler to a menu, use:
71
-
```php
72
-
/** @var Closure $listener */
73
-
$menu->setListener($listener);
74
-
```
75
-
What's **`$listener`**?
69
+
## Monitor movement of items
70
+
InvMenu comes with a listener whereby developers can write logic to monitor movement of items in and out of inventory, and thereby take action.
71
+
A listener is a callback with the following signature:
76
72
```php
77
73
/**
78
74
* @param InvMenuTransaction $transaction
79
75
*
80
-
* Must return an InvMenuTransactionResult instance.
81
76
* Return $transaction->continue() to continue the transaction.
82
77
* Return $transaction->discard() to cancel the transaction.
`InvMenuTransaction` holds all the item transction data.<br>
88
-
`InvMenuTransaction::getPlayer()` returns the `Player` that triggered the transaction.<br>
89
-
`InvMenuTransaction::getItemClicked()` returns the `Item` the player clicked in the menu.<br>
90
-
`InvMenuTransaction::getItemClickedWith()` returns the `Item` the player had in their hand when clicking an item.<br>
91
-
`InvMenuTransaction::getAction()` returns a `SlotChangeAction` instance, to get the slot index of the item clicked from the menu's inventory.<br>
92
-
`InvMenuTransaction::getTransaction()` returns the complete `InventoryTransaction` instance.<br>
82
+
-`InvMenuTransaction::getPlayer()` returns the `Player` that triggered the transaction.
83
+
-`InvMenuTransaction::getItemClicked()` returns the `Item` the player clicked in the menu. You may also use `InvMenuTransaction::getOut()`.
84
+
-`InvMenuTransaction::getItemClickedWith()` returns the `Item` the player had in their hand when clicking an item. You may also use `InvMenuTransaction::getIn()`.
85
+
-`InvMenuTransaction::getAction()` returns `SlotChangeAction` - you can get the slot that the player clicked in the menu.
86
+
-`InvMenuTransaction::getTransaction()` returns the complete `InventoryTransaction` holding all the above information.
Based on your use-case, you may find one better than the other. While `Method #1` gives you full control over a transaction (you can conditionally cancel a transaction, f.e based on whether player has permission, or player is in a specific area etc), `Method #2` reduces boilerplate `InvMenuTransactionResult` imports and calls to `InvMenutransaction::discard()`.
122
+
Alternatively, you may choose to write your own `InventoryTransactionEvent` listener that works on transactions on
123
+
`$menu->getInventory()`. However, an InvMenu listener is enough to fulfil most tasks.
133
124
134
-
## Executing a task post-transaction
135
-
A few actions are impossible to be done at the time a player is viewing an inventory, such as sending a form — a player won't be able to view a form while viewing an inventory. To do this, you will need to close the menu inventory and make sure they've closed it by waiting for a response from their side. You can do this by supplying a callback to `InvMenuTransactionResult::then()`.
125
+
## Execute a task post-transaction
126
+
Few actions are not possible to invoke at the time a player is viewing an inventory, such as sending a form—a player
127
+
cannot view a form while viewing an inventory. Close the menu and utilize `InvMenuTransactionResult::then()` callback to
$player->sendMessage("You are no longer viewing the menu.");
159
+
});
173
160
```
161
+
Inventory close listener is fired during both—server-initiated requests (i.e., `$player->removeCurrentWindow()`) and
162
+
when the player closes the inventory on their end.
174
163
175
-
## Registering a custom InvMenu type
176
-
So let's say you'd like to send players a dispenser inventory. While InvMenu doesn't ship with a `InvMenu::TYPE_DISPENSER`, you can still create a dispenser InvMenu by registering an `InvMenuType` object with the information about what a dispenser inventory looks like.
164
+
## Advanced usage: Register a custom InvMenuType
165
+
> [!IMPORTANT]
166
+
> PocketMine does not register a dispenser block. As of PocketMine v5, the task of registering missing vanilla blocks is
167
+
> excessively laborious and hence beyond the scope of this guide. [pmmp/RegisterBlocksDemoPM5](https://github.com/pmmp/RegisterBlocksDemoPM5)
168
+
> has a nice guide on how to achieve this. **Still overwhelmed?** I wrote a [drag-n-drop example plugin](https://gist.github.com/Muqsit/8884e0f75b317c332a56e01740bbfe98)
169
+
> that does all of it and registers a `/dispenser` command. With DevTools plugin installed, simply copy the code and
170
+
> paste it in a new "DispenserInvMenuPlugin.php" file in your server's plugin folder.
171
+
172
+
InvMenu does not provide a 9-slot dispenser inventory. But you can still achieve this by registering a dispenser InvMenuType.
173
+
You'll need to specify inventory size, block actor identifier (tile identifier), and the window type (network property) for
174
+
the creation of the graphic (block) and inventory parts.
177
175
```php
178
176
public const TYPE_DISPENSER = "myplugin:dispenser";
0 commit comments