> For the complete documentation index, see [llms.txt](https://docs-v4.nftx.io/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs-v4.nftx.io/contracts/zap.md).

# Zap

`NFTXZap` bundles ETH wrapping, Uniswap V4 swaps, and Locker/Listings interactions into single transactions — so a user can go straight from ETH to an NFT (or back) without juggling intermediate steps. It uses delta-based accounting and reentrancy guards to prevent donation-stealing.

Signatures and descriptions below come from the `INFTXZap` interface. Every entry point is `nonReentrant`; the ETH-in flows are `payable`.

### `buyNFTWithETH`

Buys listed NFTs with ETH in one transaction. Flow: `ETH → flETH.deposit() → swap flETH → collection token → listings.fillListings() → NFT to user`.

```solidity
function buyNFTWithETH(address _collection, uint[][] calldata _tokenIdsOut, uint _minTokensReceived, uint _maxETHSpent) external payable returns (uint ethSpent_);
```

| Parameter            | Type       | Description                                                                                                                                                                                                            |
| -------------------- | ---------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `_collection`        | `address`  | The NFT collection address                                                                                                                                                                                             |
| `_tokenIdsOut`       | `uint[][]` | Token IDs to buy, grouped by listing owner (gas optimization)                                                                                                                                                          |
| `_minTokensReceived` | `uint`     | Minimum tokens from the initial ETH→token swap (slippage protection); set from expected swap output, not listing cost                                                                                                  |
| `_maxETHSpent`       | `uint`     | Hard cap on realised ETH spend; reverts `ExcessiveInput` above it. Pass `msg.value` to opt out. Combined with `FillListingsParams.maxSpend`, protects against sandwich griefing via upward `modifyListings` front-runs |

| Return      | Type   | Description                  |
| ----------- | ------ | ---------------------------- |
| `ethSpent_` | `uint` | The ETH spent, after refunds |

### `sellNFTForETH`

Sells floor NFTs for ETH in one transaction. Flow: `NFT → locker.deposit() → swap collection token → flETH → flETH.withdraw() → ETH to user`.

```solidity
function sellNFTForETH(address _collection, uint[] calldata _tokenIds, uint _minETHReceived) external returns (uint ethReceived_);
```

| Parameter         | Type      | Description                                  |
| ----------------- | --------- | -------------------------------------------- |
| `_collection`     | `address` | The NFT collection address                   |
| `_tokenIds`       | `uint[]`  | Token IDs to sell                            |
| `_minETHReceived` | `uint`    | Minimum ETH to receive (slippage protection) |

| Return         | Type   | Description      |
| -------------- | ------ | ---------------- |
| `ethReceived_` | `uint` | The ETH received |

### `redeemFloorWithETH`

Redeems specific floor NFTs by buying the tokens with ETH and redeeming them. Flow: `ETH → swap → collection token → locker.redeem(tokenIds) → NFTs to user`.

```solidity
function redeemFloorWithETH(address _collection, uint[] calldata _tokenIds, uint _maxETHSpent) external payable returns (uint ethSpent_);
```

| Parameter      | Type      | Description                                  |
| -------------- | --------- | -------------------------------------------- |
| `_collection`  | `address` | The NFT collection address                   |
| `_tokenIds`    | `uint[]`  | Specific token IDs to redeem from the Locker |
| `_maxETHSpent` | `uint`    | Maximum ETH to spend (slippage protection)   |

| Return      | Type   | Description   |
| ----------- | ------ | ------------- |
| `ethSpent_` | `uint` | The ETH spent |

### Token swaps

Convenience swaps between ETH and a collection token, without touching NFTs.

```solidity
function buyTokensWithETH(address _collection, uint _minTokensReceived) external payable returns (uint tokensReceived_);
function sellTokensForETH(address _collection, uint _tokenAmount, uint _minETHReceived) external returns (uint ethReceived_);
function sellTokensForETHWithPermit2(address _collection, uint _tokenAmount, uint _minETHReceived, uint _deadline, uint _nonce, bytes calldata _signature) external returns (uint ethReceived_);
```

| Function                      | Key parameters                                             | Returns                                                                                         |
| ----------------------------- | ---------------------------------------------------------- | ----------------------------------------------------------------------------------------------- |
| `buyTokensWithETH`            | `_collection`, `_minTokensReceived`                        | `tokensReceived_` — collection tokens received                                                  |
| `sellTokensForETH`            | `_collection`, `_tokenAmount`, `_minETHReceived`           | `ethReceived_` — ETH received                                                                   |
| `sellTokensForETHWithPermit2` | as above, plus Permit2 `_deadline`, `_nonce`, `_signature` | `ethReceived_` — ETH received, pulling tokens via a Permit2 signature (no separate approval tx) |
