2020-04-27 16:11:54 +03:00
---
2020-10-14 21:18:55 +03:00
title: ItemStack e inventari
2020-04-27 16:11:54 +03:00
layout: default
root: ../..
idx: 2.4
2020-06-12 20:14:49 +03:00
description: Manipola gli InvRef e gli ItemStack
2020-04-27 16:11:54 +03:00
redirect_from:
2020-06-12 20:14:49 +03:00
- /it/chapters/inventories.html
- /it/chapters/itemstacks.html
- /it/inventories/inventories.html
- /it/inventories/itemstacks.html
2020-04-27 16:11:54 +03:00
---
2020-06-12 20:14:49 +03:00
## Introduzione <!-- omit in toc -->
2020-04-27 16:11:54 +03:00
2020-08-20 01:49:39 +03:00
In questo capitolo, imparerai come usare e manipolare gli inventari, siano essi quelli di un giocatore, di un nodo o a sé stanti.
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
- [Cosa sono gli ItemStack e gli inventari? ](#cosa-sono-gli-itemstack-e-gli-inventari )
- [ItemStack ](#itemstack )
- [Collocazione inventari ](#collocazione-inventari )
- [Liste ](#liste )
- [Dimensione e ampiezza ](#dimensione-e-ampiezza )
- [Controllare il contenuto ](#controllare-il-contenuto )
- [Modificare inventari e ItemStack ](#modificare-inventari-e-itemstack )
- [Aggiungere a una lista ](#aggiungere-a-una-lista )
- [Rimuovere oggetti ](#rimuovere-oggetti )
- [Manipolazione pile ](#manipolazione-pile )
- [Usura ](#usura )
- [Tabelle Lua ](#tabelle-lua )
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
## Cosa sono gli ItemStack e gli inventari?
2020-04-27 16:11:54 +03:00
2020-08-20 01:49:39 +03:00
Un ItemStack ( lett. "pila di oggetti") è il dato dietro una singola cella di un inventario.
2020-04-27 16:11:54 +03:00
2020-08-20 01:49:39 +03:00
Un *inventario* è una collezione di *liste* apposite, ognuna delle quali è una griglia 2D di ItemStack.
Lo scopo di un inventario è quello di raggruppare più liste in un singolo oggetto (l'inventario appunto), in quanto a ogni giocatore e a ogni nodo ne può essere associato massimo uno.
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
## ItemStack
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
Gli ItemStack sono composti da quattro parametri: nome, quantità, durabilità e metadati.
2020-04-27 16:11:54 +03:00
2020-08-20 01:49:39 +03:00
Il nome dell'oggetto può essere il nome di un oggetto registrato, di uno sconosciuto (non registrato) o un alias.
Gli oggetti sconosciuti sono tipici di quando si disinstallano le mod, o quando le mod rimuovono degli oggetti senza nessun accorgimento, tipo senza registrarne un alias.
2020-04-27 16:11:54 +03:00
```lua
print(stack:get_name())
stack:set_name("default:dirt")
if not stack:is_known() then
2020-06-12 20:14:49 +03:00
print("È un oggetto sconosciuto!")
2020-04-27 16:11:54 +03:00
end
```
2020-06-12 20:14:49 +03:00
La quantità sarà sempre 0 o maggiore.
2020-08-20 01:49:39 +03:00
Durante una normale sessione di gioco, la quantità non dovrebbe mai essere maggiore della dimensione massima della pila dell'oggetto - `stack_max` .
Tuttavia, comandi da amministratore e mod fallate potrebbero portare a oggetti impilati che superano la grandezza massima.
2020-04-27 16:11:54 +03:00
```lua
print(stack:get_stack_max())
```
2020-06-12 20:14:49 +03:00
Un ItemStack può essere vuoto, nel qual caso avrà come quantità 0.
2020-04-27 16:11:54 +03:00
```lua
print(stack:get_count())
stack:set_count(10)
```
2020-08-20 01:49:39 +03:00
Gli ItemStack possono poi essere creati in diversi modi usando l'omonima funzione.
2020-04-27 16:11:54 +03:00
```lua
ItemStack() -- name="", count=0
ItemStack("default:pick_stone") -- count=1
ItemStack("default:stone 30")
ItemStack({ name = "default:wood", count = 10 })
```
2020-06-12 20:14:49 +03:00
I metadati di un oggetto sono una o più coppie chiave-valore custodite in esso.
Chiave-valore significa che si usa un nome (la chiave) per accedere al dato corrispettivo (il valore).
2020-08-20 01:49:39 +03:00
Alcune chiavi hanno significati predefiniti, come `description` che è usato per specificare la descrizione di una pila di oggetti.
2020-07-02 15:34:49 +03:00
Questo sarà trattato più in dettaglio nel capitolo Storaggio e Metadati.
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
## Collocazione inventari
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
La collocazione di un inventario è dove e come un inventario viene conservato.
Ci sono tre tipi di collocazione: giocatore, nodo e separata.
Un inventario è direttamente legato a una e a una sola collocazione.
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
Gli inventari collocati nei nodi sono associati alle coordinate di un nodo specifico, come le casse.
Il nodo deve essere stato caricato perché viene salvato [nei suoi metadati ](../map/storage.html#metadata ).
2020-04-27 16:11:54 +03:00
```lua
local inv = minetest.get_inventory({ type="node", pos={x=1, y=2, z=3} })
```
2020-06-12 20:14:49 +03:00
L'esempio in alto ottiene il *riferimento a un inventario* , comunemente definito *InvRef* .
2020-08-20 01:49:39 +03:00
Questi riferimenti sono usati per manipolare l'inventario, e son chiamati così perché i dati non sono davvero salvati dentro all'oggetto (in questo caso "inv"), bensì *puntano* a quei dati.
2020-06-12 20:14:49 +03:00
In questo modo, modificando "inv", stiamo in verità modificando l'inventario.
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
La collocazione di tali riferimenti può essere ottenuta nel seguente modo:
2020-04-27 16:11:54 +03:00
```lua
local location = inv:get_location()
```
2020-08-20 01:49:39 +03:00
Gli inventari dei giocatori si ottengono in maniera simile, oppure usando il riferimento a un giocatore (*PlayerRef*).
In entrambi casi, il giocatore deve essere connesso.
2020-04-27 16:11:54 +03:00
```lua
local inv = minetest.get_inventory({ type="player", name="player1" })
2020-06-12 20:14:49 +03:00
-- oppure
2020-04-27 16:11:54 +03:00
local inv = player:get_inventory()
```
2020-08-20 01:49:39 +03:00
Gli inventari separati, infine, sono quelli non collegati né a nodi né a giocatori, e al contrario degli altri, vengono persi dopo un riavvio.
2020-04-27 16:11:54 +03:00
```lua
local inv = minetest.get_inventory({
2020-06-12 20:14:49 +03:00
type="detached", name="nome_inventario" })
2020-04-27 16:11:54 +03:00
```
2020-06-12 20:14:49 +03:00
Un'ulteriore differenza, è che gli inventari separati devono essere creati prima di poterci accedere:
2020-04-27 16:11:54 +03:00
```lua
minetest.create_detached_inventory("inventory_name")
```
2020-08-20 01:49:39 +03:00
La funzione `create_detached_inventory` accetta 3 parametri, di cui solo il primo - il nome - è necessario.
Il secondo parametro prende una tabella di callback, che possono essere utilizzati per controllare come i giocatori interagiscono con l'inventario:
2020-04-27 16:11:54 +03:00
```lua
-- Input only detached inventory
minetest.create_detached_inventory("inventory_name", {
allow_move = function(inv, from_list, from_index, to_list, to_index, count, player)
2020-06-12 20:14:49 +03:00
return count -- permette di spostare gli oggetti
2020-04-27 16:11:54 +03:00
end,
allow_put = function(inv, listname, index, stack, player)
2020-06-12 20:14:49 +03:00
return stack:get_count() -- permette di inserirli
2020-04-27 16:11:54 +03:00
end,
allow_take = function(inv, listname, index, stack, player)
2020-06-12 20:14:49 +03:00
return -1 -- non permette di rimuoverli
2020-04-27 16:11:54 +03:00
end,
on_put = function(inv, listname, index, stack, player)
minetest.chat_send_all(player:get_player_name() ..
2020-06-12 20:14:49 +03:00
" ha messo " .. stack:to_string() ..
" nella cassa delle donazioni da " .. minetest.pos_to_string(player:get_pos()))
2020-04-27 16:11:54 +03:00
end,
})
```
2020-08-20 01:49:39 +03:00
I callback dei permessi - quelle che iniziano con `allow_` - ritornano il numero degli oggetti da trasferire, e si usa -1 per impedirne del tutto l'azione.
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
I callback delle azioni - quelle che iniziano con `on_` - non ritornano invece alcun valore.
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
## Liste
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
Le liste negli inventari permettono di disporre più griglie nello stesso luogo (l'inventario).
2020-08-20 01:49:39 +03:00
Esse sono particolarmente utili per il giocatore, e infatti di base ogni gioco possiede già delle liste come *main* per il corpo principale dell'inventario e *craft* per l'area di fabbricazione.
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
### Dimensione e ampiezza
2020-04-27 16:11:54 +03:00
2020-08-20 01:49:39 +03:00
Le liste hanno una dimensione, equivalente al numero totale di celle nella griglia, e un'ampiezza, che è usata esclusivamente dentro il motore di gioco: quando viene disegnato un inventario in una finestra, infatti, il codice dietro di essa già determina che ampiezza usare.
2020-04-27 16:11:54 +03:00
```lua
if inv:set_size("main", 32) then
inv:set_width("main", 8)
2020-06-12 20:14:49 +03:00
print("dimensione: " .. inv.get_size("main"))
print("ampiezza: " .. inv:get_width("main"))
2020-04-27 16:11:54 +03:00
else
2020-06-12 20:14:49 +03:00
print("Errore! Nome dell'oggetto o dimensione non validi")
2020-04-27 16:11:54 +03:00
end
```
2020-08-20 01:49:39 +03:00
`set_size` non andrà in porto e ritornerà "false" se il nome della lista o la dimensione dichiarata non risultano valide.
Per esempio, la nuova dimensione potrebbe essere troppo piccola per contenere gli oggetti attualmente presenti nell'inventario.
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
### Controllare il contenuto
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
`is_empty` può essere usato per vedere se una lista contiene o meno degli oggetti:
2020-04-27 16:11:54 +03:00
```lua
if inv:is_empty("main") then
2020-06-12 20:14:49 +03:00
print("La lista è vuota!")
2020-04-27 16:11:54 +03:00
end
```
2020-06-12 20:14:49 +03:00
`contains_item` può invece essere usato per vedere se la lista contiene un oggetto specifico:
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
```lua
if inv:contains_item("main", "default:stone") then
print("Ho trovato della pietra!")
end
```
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
## Modificare inventari e ItemStack
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
### Aggiungere a una lista
2020-08-20 01:49:39 +03:00
Per aggiungere degli oggetti a una lista (in questo caso "main") usiamo `add_item` .
Nell'esempio sottostante ci accertiamo anche di rispettare la dimensione:
2020-04-27 16:11:54 +03:00
```lua
local stack = ItemStack("default:stone 99")
local leftover = inv:add_item("main", stack)
if leftover:get_count() > 0 then
2020-06-12 20:14:49 +03:00
print("L'inventario è pieno! " ..
leftover:get_count() .. " oggetti non sono stati aggiunti")
2020-04-27 16:11:54 +03:00
end
```
2020-06-12 20:14:49 +03:00
### Rimuovere oggetti
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
Per rimuovere oggetti da una lista, `remove_item` :
2020-04-27 16:11:54 +03:00
```lua
local taken = inv:remove_item("main", stack)
2020-06-12 20:14:49 +03:00
print("Rimossi " .. taken:get_count())
2020-04-27 16:11:54 +03:00
```
2020-06-12 20:14:49 +03:00
### Manipolare pile
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
Puoi modificare le singole pile prima ottenendole:
2020-04-27 16:11:54 +03:00
```lua
local stack = inv:get_stack(listname, 0)
```
2020-08-20 01:49:39 +03:00
E poi modificandole impostando le nuove proprietà o usando i metodi che rispettano `stack_size` :
2020-04-27 16:11:54 +03:00
```lua
2020-06-12 20:14:49 +03:00
local pila = ItemStack("default:stone 50")
local da_aggiungere = ItemStack("default:stone 100")
local resto = pila:add_item(da_aggiungere)
local rimossi = pila:take_item(19)
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
print("Impossibile aggiungere " .. resto:get_count() .. " degli oggetti.")
-- ^ sarà 51
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
print("Hai " .. pila:get_count() .. " oggetti")
-- ^ sarà 80
2020-04-27 16:11:54 +03:00
-- min(50+100, stack_max) - 19 = 80
2020-06-12 20:14:49 +03:00
-- dove stack_max = 99
2020-04-27 16:11:54 +03:00
```
2020-06-12 20:14:49 +03:00
`add_item` aggiungerà gli oggetti all'ItemStack e ritornerà quelli in eccesso.
2020-08-20 01:49:39 +03:00
`take_item` rimuoverà gli oggetti indicati (o meno se ce ne sono meno), e ritornerà l'ammontare rimosso.
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
Infine, si imposta la pila modificata:
2020-04-27 16:11:54 +03:00
```lua
2020-06-12 20:14:49 +03:00
inv:set_stack(listname, 0, pila)
2020-04-27 16:11:54 +03:00
```
2020-06-12 20:14:49 +03:00
## Usura
2020-04-27 16:11:54 +03:00
2020-08-20 01:49:39 +03:00
Gli strumenti possono avere un livello di usura; essa è rappresentata da un barra progressiva e fa rompere lo strumento quando completamente logorato.
Nello specifico, l'usura è un numero da 0 a 65535: più è alto, più è consumato l'oggetto.
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
Il livello di usura può essere manipolato usando `add_wear()` , `get_wear()` , e `set_wear(wear)` .
2020-04-27 16:11:54 +03:00
```lua
2020-06-12 20:14:49 +03:00
local pila = ItemStack("default:pick_mese")
local usi_massimi = 10
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
-- Questo viene fatto in automatico quando usi uno strumento che scava cose.
-- Aumenta l'usura dell'oggetto dopo un uso
pila:add_wear(65535 / (usi_massimi - 1))
2020-04-27 16:11:54 +03:00
```
2020-08-20 01:49:39 +03:00
Quando si scava un nodo, l'incremento di usura di uno strumento dipende da che tipo di nodo è.
2020-06-12 20:14:49 +03:00
Di conseguenza, `usi_massimi` varia a seconda di cos'è stato scavato.
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
## Tabelle Lua
2020-04-27 16:11:54 +03:00
2020-06-12 20:14:49 +03:00
Gli ItemStack e gli inventari possono essere convertiti in/dalle tabelle.
Questo è utile per operazioni di copiatura e immagazzinaggio.
2020-04-27 16:11:54 +03:00
```lua
2020-06-12 20:14:49 +03:00
-- Inventario intero
2020-04-27 16:11:54 +03:00
local data = inv1:get_lists()
inv2:set_lists(data)
2020-06-12 20:14:49 +03:00
-- Una lista
2020-04-27 16:11:54 +03:00
local listdata = inv1:get_list("main")
inv2:set_list("main", listdata)
```
2020-06-12 20:14:49 +03:00
La tabella di liste ritornata da `get_lists()` sarà nel seguente formato:
2020-04-27 16:11:54 +03:00
```lua
{
2020-06-12 20:14:49 +03:00
lista_uno = {
2020-04-27 16:11:54 +03:00
ItemStack,
ItemStack,
ItemStack,
ItemStack,
2020-06-12 20:14:49 +03:00
-- inv:get_size("lista_uno") elementi
2020-04-27 16:11:54 +03:00
},
2020-06-12 20:14:49 +03:00
lista_due = {
2020-04-27 16:11:54 +03:00
ItemStack,
ItemStack,
ItemStack,
ItemStack,
2020-06-12 20:14:49 +03:00
-- inv:get_size("lista_due") elementi
2020-04-27 16:11:54 +03:00
}
}
```
2020-06-12 20:14:49 +03:00
`get_list()` ritornerà una lista singola fatta di ItemStack.
2020-04-27 16:11:54 +03:00
2020-08-20 01:49:39 +03:00
Una cosa importante da sottolineare è che i metodi `set` qui in alto non cambiano la dimensione delle liste.
Questo significa che si può svuotare una lista dichiarandola uguale a una tabella vuota, e la sua dimensione tuttavia non cambierà:
2020-04-27 16:11:54 +03:00
```lua
inv:set_list("main", {})
```