tutorial:transfer-api_storage
Differences
This shows you the differences between two versions of the page.
| Both sides previous revisionPrevious revisionNext revision | Previous revision | ||
| tutorial:transfer-api_storage [2021/10/30 09:31] – technici4n | tutorial:transfer-api_storage [2021/10/30 10:25] (current) – external edit 127.0.0.1 | ||
|---|---|---|---|
| Line 1: | Line 1: | ||
| - | ===== Fabric Transfer API: Understanding Storage<T> ===== | + | ===== Fabric Transfer API: Understanding Storage<FluidVariant> ===== |
| //This article is part of a series on the Fabric Transfer API. [[tutorial: | //This article is part of a series on the Fabric Transfer API. [[tutorial: | ||
| + | **'' | ||
| + | |||
| + | ==== You already used Storage< | ||
| [[tutorial: | [[tutorial: | ||
| <code java> | <code java> | ||
| Line 8: | Line 11: | ||
| </ | </ | ||
| - | The takeaway here is that '' | + | The takeaway here is that '' |
| - | + | ||
| - | **'' | + | |
| + | ==== Retrieving a Storage< | ||
| Let's see how we can retrieve one from the world: | Let's see how we can retrieve one from the world: | ||
| <code java> | <code java> | ||
| Line 24: | Line 26: | ||
| } | } | ||
| </ | </ | ||
| + | |||
| + | ==== A look at Storage< | ||
| + | Let's have a look at '' | ||
| + | <code java> | ||
| + | public interface Storage< | ||
| + | // Try to insert a resource in the storage, return how much was inserted. | ||
| + | long insert(T resource, long maxAmount, TransactionContext transaction); | ||
| + | // Try to extract a resource from the storage, return how much was extracted. | ||
| + | long extract(T resource, long maxAmount, TransactionContext transaction); | ||
| + | // Iterate over the contents of this storage. | ||
| + | default Iterable< | ||
| + | |||
| + | ... | ||
| + | } | ||
| + | </ | ||
| + | This interface allows us to insert into a storage, extract from it, and read its contents. | ||
| + | |||
| + | ==== First example: how to insert exactly one bucket of water into a storage ==== | ||
| + | <code java> | ||
| + | Storage< | ||
| + | FluidVariant water = FluidVariant.of(Fluids.WATER); | ||
| + | |||
| + | // Open a transaction: | ||
| + | try (Transaction transaction = Transaction.openOuter()) { | ||
| + | // Try to insert, will return how much was actually inserted. | ||
| + | long amountInserted = storage.insert(water, | ||
| + | if (amountInserted == FluidConstants.BUCKET) { | ||
| + | // " | ||
| + | // You should call this if you are satisfied with the result of the operation, and want to keep it. | ||
| + | transaction.commit(); | ||
| + | } else { | ||
| + | // Doing nothing " | ||
| + | // You should call this if you are not satisfied with the result of the operation, and want to abort it. | ||
| + | } | ||
| + | } | ||
| + | </ | ||
| + | |||
| + | ==== Second example: move exactly one bucket of lava from a storage to another storage ==== | ||
| + | <code java> | ||
| + | import static net.fabricmc.fabric.api.transfer.v1.fluid.FluidConstants.BUCKET; | ||
| + | |||
| + | Storage< | ||
| + | FluidVariant lava = FluidVariant.of(Fluids.LAVA); | ||
| + | |||
| + | try (Transaction transaction = Transaction.openOuter()) { | ||
| + | if (source.extract(lava, | ||
| + | transaction.commit(); | ||
| + | } | ||
| + | } | ||
| + | </ | ||
| + | Hopefully you understand why this works, and why this will never duplicate or void fluid. | ||
| + | |||
| + | ==== A more complicated example: Extracting the contents of a storage ==== | ||
| + | In the previous example, we knew that we wanted to move water or lava. But what if we don't know what to extract? The answer is: iterate over the contents! | ||
| + | This example also introduces the concept of nested transactions. | ||
| + | <code java> | ||
| + | Storage< | ||
| + | Predicate< | ||
| + | long totalExtracted = 0; | ||
| + | |||
| + | // Open a transaction, | ||
| + | try (Transaction transaction = Transaction.openOuter()) { | ||
| + | // Loop over the contents! Each StorageView< | ||
| + | for (StorageView< | ||
| + | if (view.isResourceBlank()) continue; // This means that the view contains no resource, represented by FluidVariant.blank(). | ||
| + | FluidVariant storedResource = view.getResource(); | ||
| + | if (!filter.test(storedResource)) continue; // The filter rejected this resource, skip it. | ||
| + | |||
| + | // If you want to extract any amount <= view.getAmount(), | ||
| + | totalExtracted += view.extract(storedResource, | ||
| + | |||
| + | // If you want to extract either the exact amount or nothing, you can use a nested transaction! | ||
| + | try (Transaction nestedTransaction = transaction.openNested()) { | ||
| + | long amount = view.getAmount(); | ||
| + | long extracted = view.extract(storedResource, | ||
| + | if (extracted == amount) { | ||
| + | totalExtracted += amount; | ||
| + | nestedTransaction.commit(); | ||
| + | } else { | ||
| + | // If we do nothing, the extraction is cancelled immediately when nestedTransaction is closed at the end of the try { ... } block. | ||
| + | } | ||
| + | } | ||
| + | } | ||
| + | transaction.commit(); | ||
| + | } | ||
| + | </ | ||
| + | |||
| + | ==== Conclusion ==== | ||
| + | You should now be able to use '' | ||
| + | |||
| + | You should also have a look at '' | ||
| + | |||
tutorial/transfer-api_storage.1635586269.txt.gz · Last modified: 2021/10/30 09:31 by technici4n