编译器
0.8.13+commit.abaa5c0e
文件 1 的 18:Address.sol
pragma solidity ^0.8.1;
library Address {
function isContract(address account) internal view returns (bool) {
return account.code.length > 0;
}
function sendValue(address payable recipient, uint256 amount) internal {
require(address(this).balance >= amount, "Address: insufficient balance");
(bool success, ) = recipient.call{value: amount}("");
require(success, "Address: unable to send value, recipient may have reverted");
}
function functionCall(address target, bytes memory data) internal returns (bytes memory) {
return functionCall(target, data, "Address: low-level call failed");
}
function functionCall(
address target,
bytes memory data,
string memory errorMessage
) internal returns (bytes memory) {
return functionCallWithValue(target, data, 0, errorMessage);
}
function functionCallWithValue(
address target,
bytes memory data,
uint256 value
) internal returns (bytes memory) {
return functionCallWithValue(target, data, value, "Address: low-level call with value failed");
}
function functionCallWithValue(
address target,
bytes memory data,
uint256 value,
string memory errorMessage
) internal returns (bytes memory) {
require(address(this).balance >= value, "Address: insufficient balance for call");
require(isContract(target), "Address: call to non-contract");
(bool success, bytes memory returndata) = target.call{value: value}(data);
return verifyCallResult(success, returndata, errorMessage);
}
function functionStaticCall(address target, bytes memory data) internal view returns (bytes memory) {
return functionStaticCall(target, data, "Address: low-level static call failed");
}
function functionStaticCall(
address target,
bytes memory data,
string memory errorMessage
) internal view returns (bytes memory) {
require(isContract(target), "Address: static call to non-contract");
(bool success, bytes memory returndata) = target.staticcall(data);
return verifyCallResult(success, returndata, errorMessage);
}
function functionDelegateCall(address target, bytes memory data) internal returns (bytes memory) {
return functionDelegateCall(target, data, "Address: low-level delegate call failed");
}
function functionDelegateCall(
address target,
bytes memory data,
string memory errorMessage
) internal returns (bytes memory) {
require(isContract(target), "Address: delegate call to non-contract");
(bool success, bytes memory returndata) = target.delegatecall(data);
return verifyCallResult(success, returndata, errorMessage);
}
function verifyCallResult(
bool success,
bytes memory returndata,
string memory errorMessage
) internal pure returns (bytes memory) {
if (success) {
return returndata;
} else {
if (returndata.length > 0) {
assembly {
let returndata_size := mload(returndata)
revert(add(32, returndata), returndata_size)
}
} else {
revert(errorMessage);
}
}
}
}
文件 2 的 18:Base64.sol
pragma solidity ^0.8.0;
library Base64 {
string internal constant _TABLE = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
function encode(bytes memory data) internal pure returns (string memory) {
if (data.length == 0) return "";
string memory table = _TABLE;
string memory result = new string(4 * ((data.length + 2) / 3));
assembly {
let tablePtr := add(table, 1)
let resultPtr := add(result, 32)
for {
let dataPtr := data
let endPtr := add(data, mload(data))
} lt(dataPtr, endPtr) {
} {
dataPtr := add(dataPtr, 3)
let input := mload(dataPtr)
mstore8(resultPtr, mload(add(tablePtr, and(shr(18, input), 0x3F))))
resultPtr := add(resultPtr, 1)
mstore8(resultPtr, mload(add(tablePtr, and(shr(12, input), 0x3F))))
resultPtr := add(resultPtr, 1)
mstore8(resultPtr, mload(add(tablePtr, and(shr(6, input), 0x3F))))
resultPtr := add(resultPtr, 1)
mstore8(resultPtr, mload(add(tablePtr, and(input, 0x3F))))
resultPtr := add(resultPtr, 1)
}
switch mod(mload(data), 3)
case 1 {
mstore8(sub(resultPtr, 1), 0x3d)
mstore8(sub(resultPtr, 2), 0x3d)
}
case 2 {
mstore8(sub(resultPtr, 1), 0x3d)
}
}
return result;
}
}
文件 3 的 18:Context.sol
pragma solidity ^0.8.0;
abstract contract Context {
function _msgSender() internal view virtual returns (address) {
return msg.sender;
}
function _msgData() internal view virtual returns (bytes calldata) {
return msg.data;
}
}
文件 4 的 18:ERC165.sol
pragma solidity ^0.8.0;
import "./IERC165.sol";
abstract contract ERC165 is IERC165 {
function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool) {
return interfaceId == type(IERC165).interfaceId;
}
}
文件 5 的 18:ERC721A.sol
pragma solidity ^0.8.4;
import "../interfaces/IERC721A.sol";
import "@openzeppelin/contracts/token/ERC721/IERC721Receiver.sol";
import "@openzeppelin/contracts/utils/Address.sol";
import "@openzeppelin/contracts/utils/Context.sol";
import "@openzeppelin/contracts/utils/Strings.sol";
import "@openzeppelin/contracts/utils/introspection/ERC165.sol";
contract ERC721A is Context, ERC165, IERC721A {
using Address for address;
using Strings for uint256;
uint256 internal _currentIndex;
uint256 internal _burnCounter;
string private _name;
string private _symbol;
mapping(uint256 => TokenOwnership) internal _ownerships;
mapping(address => AddressData) private _addressData;
mapping(uint256 => address) private _tokenApprovals;
mapping(address => mapping(address => bool)) private _operatorApprovals;
constructor(string memory name_, string memory symbol_) {
_name = name_;
_symbol = symbol_;
_currentIndex = _startTokenId();
}
function _startTokenId() internal view virtual returns (uint256) {
return 0;
}
function totalSupply() public view override returns (uint256) {
unchecked {
return _currentIndex - _burnCounter - _startTokenId();
}
}
function _totalMinted() internal view returns (uint256) {
unchecked {
return _currentIndex - _startTokenId();
}
}
function supportsInterface(bytes4 interfaceId)
public
view
virtual
override(ERC165, IERC165)
returns (bool)
{
return
interfaceId == type(IERC721).interfaceId ||
interfaceId == type(IERC721Metadata).interfaceId ||
super.supportsInterface(interfaceId);
}
function balanceOf(address owner) public view override returns (uint256) {
if (owner == address(0)) revert BalanceQueryForZeroAddress();
return uint256(_addressData[owner].balance);
}
function _numberMinted(address owner) internal view returns (uint256) {
return uint256(_addressData[owner].numberMinted);
}
function _numberBurned(address owner) internal view returns (uint256) {
return uint256(_addressData[owner].numberBurned);
}
function _getAux(address owner) internal view returns (uint64) {
return _addressData[owner].aux;
}
function _setAux(address owner, uint64 aux) internal {
_addressData[owner].aux = aux;
}
function _ownershipOf(uint256 tokenId)
internal
view
returns (TokenOwnership memory)
{
uint256 curr = tokenId;
unchecked {
if (_startTokenId() <= curr && curr < _currentIndex) {
TokenOwnership memory ownership = _ownerships[curr];
if (!ownership.burned) {
if (ownership.addr != address(0)) {
return ownership;
}
while (true) {
curr--;
ownership = _ownerships[curr];
if (ownership.addr != address(0)) {
return ownership;
}
}
}
}
}
revert OwnerQueryForNonexistentToken();
}
function ownerOf(uint256 tokenId) public view override returns (address) {
return _ownershipOf(tokenId).addr;
}
function name() public view virtual override returns (string memory) {
return _name;
}
function symbol() public view virtual override returns (string memory) {
return _symbol;
}
function tokenURI(uint256 tokenId)
public
view
virtual
override
returns (string memory)
{
if (!_exists(tokenId)) revert URIQueryForNonexistentToken();
string memory baseURI = _baseURI();
return
bytes(baseURI).length != 0
? string(abi.encodePacked(baseURI, tokenId.toString()))
: "";
}
function _baseURI() internal view virtual returns (string memory) {
return "";
}
function approve(address to, uint256 tokenId) public override {
address owner = ERC721A.ownerOf(tokenId);
if (to == owner) revert ApprovalToCurrentOwner();
if (_msgSender() != owner && !isApprovedForAll(owner, _msgSender())) {
revert ApprovalCallerNotOwnerNorApproved();
}
_approve(to, tokenId, owner);
}
function getApproved(uint256 tokenId)
public
view
override
returns (address)
{
if (!_exists(tokenId)) revert ApprovalQueryForNonexistentToken();
return _tokenApprovals[tokenId];
}
function setApprovalForAll(address operator, bool approved)
public
virtual
override
{
if (operator == _msgSender()) revert ApproveToCaller();
_operatorApprovals[_msgSender()][operator] = approved;
emit ApprovalForAll(_msgSender(), operator, approved);
}
function isApprovedForAll(address owner, address operator)
public
view
virtual
override
returns (bool)
{
return _operatorApprovals[owner][operator];
}
function transferFrom(
address from,
address to,
uint256 tokenId
) public virtual override {
_transfer(from, to, tokenId);
}
function safeTransferFrom(
address from,
address to,
uint256 tokenId
) public virtual override {
safeTransferFrom(from, to, tokenId, "");
}
function safeTransferFrom(
address from,
address to,
uint256 tokenId,
bytes memory _data
) public virtual override {
_transfer(from, to, tokenId);
if (
to.isContract() &&
!_checkContractOnERC721Received(from, to, tokenId, _data)
) {
revert TransferToNonERC721ReceiverImplementer();
}
}
function _exists(uint256 tokenId) internal view returns (bool) {
return
_startTokenId() <= tokenId &&
tokenId < _currentIndex &&
!_ownerships[tokenId].burned;
}
function _safeMint(address to, uint256 quantity) internal {
_safeMint(to, quantity, "");
}
function _safeMint(
address to,
uint256 quantity,
bytes memory _data
) internal {
uint256 startTokenId = _currentIndex;
if (to == address(0)) revert MintToZeroAddress();
if (quantity == 0) revert MintZeroQuantity();
_beforeTokenTransfers(address(0), to, startTokenId, quantity);
unchecked {
_addressData[to].balance += uint64(quantity);
_addressData[to].numberMinted += uint64(quantity);
_ownerships[startTokenId].addr = to;
_ownerships[startTokenId].startTimestamp = uint64(block.timestamp);
uint256 updatedIndex = startTokenId;
uint256 end = updatedIndex + quantity;
if (to.isContract()) {
do {
emit Transfer(address(0), to, updatedIndex);
if (
!_checkContractOnERC721Received(
address(0),
to,
updatedIndex++,
_data
)
) {
revert TransferToNonERC721ReceiverImplementer();
}
} while (updatedIndex < end);
if (_currentIndex != startTokenId) revert();
} else {
do {
emit Transfer(address(0), to, updatedIndex++);
} while (updatedIndex < end);
}
_currentIndex = updatedIndex;
}
_afterTokenTransfers(address(0), to, startTokenId, quantity);
}
function _mint(address to, uint256 quantity) internal {
uint256 startTokenId = _currentIndex;
if (to == address(0)) revert MintToZeroAddress();
if (quantity == 0) revert MintZeroQuantity();
_beforeTokenTransfers(address(0), to, startTokenId, quantity);
unchecked {
_addressData[to].balance += uint64(quantity);
_addressData[to].numberMinted += uint64(quantity);
_ownerships[startTokenId].addr = to;
_ownerships[startTokenId].startTimestamp = uint64(block.timestamp);
uint256 updatedIndex = startTokenId;
uint256 end = updatedIndex + quantity;
do {
emit Transfer(address(0), to, updatedIndex++);
} while (updatedIndex < end);
_currentIndex = updatedIndex;
}
_afterTokenTransfers(address(0), to, startTokenId, quantity);
}
function _transfer(
address from,
address to,
uint256 tokenId
) private {
TokenOwnership memory prevOwnership = _ownershipOf(tokenId);
if (prevOwnership.addr != from) revert TransferFromIncorrectOwner();
bool isApprovedOrOwner = (_msgSender() == from ||
isApprovedForAll(from, _msgSender()) ||
getApproved(tokenId) == _msgSender());
if (!isApprovedOrOwner) revert TransferCallerNotOwnerNorApproved();
if (to == address(0)) revert TransferToZeroAddress();
_beforeTokenTransfers(from, to, tokenId, 1);
_approve(address(0), tokenId, from);
unchecked {
_addressData[from].balance -= 1;
_addressData[to].balance += 1;
TokenOwnership storage currSlot = _ownerships[tokenId];
currSlot.addr = to;
currSlot.startTimestamp = uint64(block.timestamp);
uint256 nextTokenId = tokenId + 1;
TokenOwnership storage nextSlot = _ownerships[nextTokenId];
if (nextSlot.addr == address(0)) {
if (nextTokenId != _currentIndex) {
nextSlot.addr = from;
nextSlot.startTimestamp = prevOwnership.startTimestamp;
}
}
}
emit Transfer(from, to, tokenId);
_afterTokenTransfers(from, to, tokenId, 1);
}
function _burn(uint256 tokenId) internal virtual {
_burn(tokenId, false);
}
function _burn(uint256 tokenId, bool approvalCheck) internal virtual {
TokenOwnership memory prevOwnership = _ownershipOf(tokenId);
address from = prevOwnership.addr;
if (approvalCheck) {
bool isApprovedOrOwner = (_msgSender() == from ||
isApprovedForAll(from, _msgSender()) ||
getApproved(tokenId) == _msgSender());
if (!isApprovedOrOwner) revert TransferCallerNotOwnerNorApproved();
}
_beforeTokenTransfers(from, address(0), tokenId, 1);
_approve(address(0), tokenId, from);
unchecked {
AddressData storage addressData = _addressData[from];
addressData.balance -= 1;
addressData.numberBurned += 1;
TokenOwnership storage currSlot = _ownerships[tokenId];
currSlot.addr = from;
currSlot.startTimestamp = uint64(block.timestamp);
currSlot.burned = true;
uint256 nextTokenId = tokenId + 1;
TokenOwnership storage nextSlot = _ownerships[nextTokenId];
if (nextSlot.addr == address(0)) {
if (nextTokenId != _currentIndex) {
nextSlot.addr = from;
nextSlot.startTimestamp = prevOwnership.startTimestamp;
}
}
}
emit Transfer(from, address(0), tokenId);
_afterTokenTransfers(from, address(0), tokenId, 1);
unchecked {
_burnCounter++;
}
}
function _approve(
address to,
uint256 tokenId,
address owner
) private {
_tokenApprovals[tokenId] = to;
emit Approval(owner, to, tokenId);
}
function _checkContractOnERC721Received(
address from,
address to,
uint256 tokenId,
bytes memory _data
) private returns (bool) {
try
IERC721Receiver(to).onERC721Received(
_msgSender(),
from,
tokenId,
_data
)
returns (bytes4 retval) {
return retval == IERC721Receiver(to).onERC721Received.selector;
} catch (bytes memory reason) {
if (reason.length == 0) {
revert TransferToNonERC721ReceiverImplementer();
} else {
assembly {
revert(add(32, reason), mload(reason))
}
}
}
}
function _beforeTokenTransfers(
address from,
address to,
uint256 startTokenId,
uint256 quantity
) internal virtual {}
function _afterTokenTransfers(
address from,
address to,
uint256 startTokenId,
uint256 quantity
) internal virtual {}
}
文件 6 的 18:IERC165.sol
pragma solidity ^0.8.0;
interface IERC165 {
function supportsInterface(bytes4 interfaceId) external view returns (bool);
}
文件 7 的 18:IERC721.sol
pragma solidity ^0.8.0;
import "../../utils/introspection/IERC165.sol";
interface IERC721 is IERC165 {
event Transfer(address indexed from, address indexed to, uint256 indexed tokenId);
event Approval(address indexed owner, address indexed approved, uint256 indexed tokenId);
event ApprovalForAll(address indexed owner, address indexed operator, bool approved);
function balanceOf(address owner) external view returns (uint256 balance);
function ownerOf(uint256 tokenId) external view returns (address owner);
function safeTransferFrom(
address from,
address to,
uint256 tokenId
) external;
function transferFrom(
address from,
address to,
uint256 tokenId
) external;
function approve(address to, uint256 tokenId) external;
function getApproved(uint256 tokenId) external view returns (address operator);
function setApprovalForAll(address operator, bool _approved) external;
function isApprovedForAll(address owner, address operator) external view returns (bool);
function safeTransferFrom(
address from,
address to,
uint256 tokenId,
bytes calldata data
) external;
}
文件 8 的 18:IERC721A.sol
pragma solidity ^0.8.4;
import "@openzeppelin/contracts/token/ERC721/IERC721.sol";
import "@openzeppelin/contracts/token/ERC721/extensions/IERC721Metadata.sol";
interface IERC721A is IERC721, IERC721Metadata {
error ApprovalCallerNotOwnerNorApproved();
error ApprovalQueryForNonexistentToken();
error ApproveToCaller();
error ApprovalToCurrentOwner();
error BalanceQueryForZeroAddress();
error MintToZeroAddress();
error MintZeroQuantity();
error OwnerQueryForNonexistentToken();
error TransferCallerNotOwnerNorApproved();
error TransferFromIncorrectOwner();
error TransferToNonERC721ReceiverImplementer();
error TransferToZeroAddress();
error URIQueryForNonexistentToken();
struct TokenOwnership {
address addr;
uint64 startTimestamp;
bool burned;
}
struct AddressData {
uint64 balance;
uint64 numberMinted;
uint64 numberBurned;
uint64 aux;
}
function totalSupply() external view returns (uint256);
}
文件 9 的 18:IERC721Metadata.sol
pragma solidity ^0.8.0;
import "../IERC721.sol";
interface IERC721Metadata is IERC721 {
function name() external view returns (string memory);
function symbol() external view returns (string memory);
function tokenURI(uint256 tokenId) external view returns (string memory);
}
文件 10 的 18:IERC721Receiver.sol
pragma solidity ^0.8.0;
interface IERC721Receiver {
function onERC721Received(
address operator,
address from,
uint256 tokenId,
bytes calldata data
) external returns (bytes4);
}
文件 11 的 18:ITreasure.sol
pragma solidity ^0.8.9;
interface ITreasure {
function plunder(uint256 numMints) external payable;
function status() external view returns (bool);
function contractURI() external view returns (string memory);
function reserved() external view returns (uint256);
function price() external pure returns (uint256);
}
文件 12 的 18:Ownable.sol
pragma solidity ^0.8.0;
import "../utils/Context.sol";
abstract contract Ownable is Context {
address private _owner;
event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);
constructor() {
_transferOwnership(_msgSender());
}
function owner() public view virtual returns (address) {
return _owner;
}
modifier onlyOwner() {
require(owner() == _msgSender(), "Ownable: caller is not the owner");
_;
}
function renounceOwnership() public virtual onlyOwner {
_transferOwnership(address(0));
}
function transferOwnership(address newOwner) public virtual onlyOwner {
require(newOwner != address(0), "Ownable: new owner is the zero address");
_transferOwnership(newOwner);
}
function _transferOwnership(address newOwner) internal virtual {
address oldOwner = _owner;
_owner = newOwner;
emit OwnershipTransferred(oldOwner, newOwner);
}
}
文件 13 的 18:PaymentSplitter.sol
pragma solidity ^0.8.0;
import "@openzeppelin/contracts/utils/Address.sol";
import "@openzeppelin/contracts/utils/Context.sol";
import "@openzeppelin/contracts/utils/math/SafeMath.sol";
contract PaymentSplitter is Context {
event PayeeAdded(address account, uint256 shares);
event PaymentReleased(address to, uint256 amount);
event PaymentReceived(address from, uint256 amount);
uint256 private _totalShares;
uint256 private _totalReleased;
mapping(address => uint256) private _shares;
mapping(address => uint256) private _released;
address[] private _payees;
constructor(address[] memory payees, uint256[] memory shares_) payable {
require(
payees.length == shares_.length,
"PaymentSplitter: payees and shares length mismatch"
);
require(payees.length > 0, "PaymentSplitter: no payees");
for (uint256 i = 0; i < payees.length; i++) {
_addPayee(payees[i], shares_[i]);
}
}
receive() external payable virtual {
emit PaymentReceived(_msgSender(), msg.value);
}
function totalShares() public view returns (uint256) {
return _totalShares;
}
function totalReleased() public view returns (uint256) {
return _totalReleased;
}
function shares(address account) public view returns (uint256) {
return _shares[account];
}
function released(address account) public view returns (uint256) {
return _released[account];
}
function payee(uint256 index) public view returns (address) {
return _payees[index];
}
function release(address payable account) public virtual {
require(_shares[account] > 0, "PaymentSplitter: account has no shares");
uint256 totalReceived = address(this).balance + _totalReleased;
uint256 payment = (totalReceived * _shares[account]) /
_totalShares -
_released[account];
require(payment != 0, "PaymentSplitter: account is not due payment");
_released[account] = _released[account] + payment;
_totalReleased = _totalReleased + payment;
Address.sendValue(account, payment);
emit PaymentReleased(account, payment);
}
function _addPayee(address account, uint256 shares_) private {
require(
account != address(0),
"PaymentSplitter: account is the zero address"
);
require(shares_ > 0, "PaymentSplitter: shares are 0");
require(
_shares[account] == 0,
"PaymentSplitter: account already has shares"
);
_payees.push(account);
_shares[account] = shares_;
_totalShares = _totalShares + shares_;
emit PayeeAdded(account, shares_);
}
}
文件 14 的 18:ReentrancyGuard.sol
pragma solidity ^0.8.0;
abstract contract ReentrancyGuard {
uint256 private constant _NOT_ENTERED = 1;
uint256 private constant _ENTERED = 2;
uint256 private _status;
constructor() {
_status = _NOT_ENTERED;
}
modifier nonReentrant() {
require(_status != _ENTERED, "ReentrancyGuard: reentrant call");
_status = _ENTERED;
_;
_status = _NOT_ENTERED;
}
}
文件 15 的 18:SafeMath.sol
pragma solidity ^0.8.0;
library SafeMath {
function tryAdd(uint256 a, uint256 b) internal pure returns (bool, uint256) {
unchecked {
uint256 c = a + b;
if (c < a) return (false, 0);
return (true, c);
}
}
function trySub(uint256 a, uint256 b) internal pure returns (bool, uint256) {
unchecked {
if (b > a) return (false, 0);
return (true, a - b);
}
}
function tryMul(uint256 a, uint256 b) internal pure returns (bool, uint256) {
unchecked {
if (a == 0) return (true, 0);
uint256 c = a * b;
if (c / a != b) return (false, 0);
return (true, c);
}
}
function tryDiv(uint256 a, uint256 b) internal pure returns (bool, uint256) {
unchecked {
if (b == 0) return (false, 0);
return (true, a / b);
}
}
function tryMod(uint256 a, uint256 b) internal pure returns (bool, uint256) {
unchecked {
if (b == 0) return (false, 0);
return (true, a % b);
}
}
function add(uint256 a, uint256 b) internal pure returns (uint256) {
return a + b;
}
function sub(uint256 a, uint256 b) internal pure returns (uint256) {
return a - b;
}
function mul(uint256 a, uint256 b) internal pure returns (uint256) {
return a * b;
}
function div(uint256 a, uint256 b) internal pure returns (uint256) {
return a / b;
}
function mod(uint256 a, uint256 b) internal pure returns (uint256) {
return a % b;
}
function sub(
uint256 a,
uint256 b,
string memory errorMessage
) internal pure returns (uint256) {
unchecked {
require(b <= a, errorMessage);
return a - b;
}
}
function div(
uint256 a,
uint256 b,
string memory errorMessage
) internal pure returns (uint256) {
unchecked {
require(b > 0, errorMessage);
return a / b;
}
}
function mod(
uint256 a,
uint256 b,
string memory errorMessage
) internal pure returns (uint256) {
unchecked {
require(b > 0, errorMessage);
return a % b;
}
}
}
文件 16 的 18:Strings.sol
pragma solidity ^0.8.0;
library Strings {
bytes16 private constant _HEX_SYMBOLS = "0123456789abcdef";
function toString(uint256 value) internal pure returns (string memory) {
if (value == 0) {
return "0";
}
uint256 temp = value;
uint256 digits;
while (temp != 0) {
digits++;
temp /= 10;
}
bytes memory buffer = new bytes(digits);
while (value != 0) {
digits -= 1;
buffer[digits] = bytes1(uint8(48 + uint256(value % 10)));
value /= 10;
}
return string(buffer);
}
function toHexString(uint256 value) internal pure returns (string memory) {
if (value == 0) {
return "0x00";
}
uint256 temp = value;
uint256 length = 0;
while (temp != 0) {
length++;
temp >>= 8;
}
return toHexString(value, length);
}
function toHexString(uint256 value, uint256 length) internal pure returns (string memory) {
bytes memory buffer = new bytes(2 * length + 2);
buffer[0] = "0";
buffer[1] = "x";
for (uint256 i = 2 * length + 1; i > 1; --i) {
buffer[i] = _HEX_SYMBOLS[value & 0xf];
value >>= 4;
}
require(value == 0, "Strings: hex length insufficient");
return string(buffer);
}
}
文件 17 的 18:Treasure.sol
pragma solidity ^0.8.13;
import "./ERC721A.sol";
import "@openzeppelin/contracts/security/ReentrancyGuard.sol";
import "./PaymentSplitter.sol";
import "@openzeppelin/contracts/utils/Address.sol";
import "@openzeppelin/contracts/access/Ownable.sol";
import "./TreasureMetadata.sol";
import "../interfaces/ITreasure.sol";
contract Treasure is
ERC721A,
Ownable,
ReentrancyGuard,
PaymentSplitter,
TreasureMetadata,
ITreasure
{
uint256 private constant PRICE = 0.0420 ether;
uint256 private constant MAX_SUPPLY = 10000;
uint256 private constant MAX_MULTIMINT = 25;
uint256 private constant MAX_RESERVE = 250;
address[] private _payees = [
0x4f65cDFfE6c48ad287f005AD14E78ff6433c8d67,
0x49B621D1Cc662cE293779EC775573d0568a0c713,
0x4427fCC55d41f5eD6989Fc7c6AC1542653192b05,
0x3b20f287b08f39c21D695500E08268c87eCaeB37
];
uint256[] private _shares = [20, 14, 33, 33];
string private _contractURI;
bool private _status = false;
uint256 private _reserved = 0;
constructor(
Item memory __head,
Item memory __torso,
Item memory __footwear,
Item memory __bottoms,
Item memory __weapon,
Item memory __shield,
Item memory __amulet,
Item memory __possessive,
Item memory __extra,
Item memory __material,
Item memory __tail
)
ERC721A("Treasure (for Warriors)", "T4W")
PaymentSplitter(_payees, _shares)
TreasureMetadata(
__head,
__torso,
__footwear,
__bottoms,
__weapon,
__shield,
__amulet,
__possessive,
__extra,
__material,
__tail
)
{}
function plunder(uint256 numMints) external payable override nonReentrant {
require(_status, "Sale is paused");
require(msg.value >= price() * numMints, "Not enough ether sent");
require(
totalSupply() + numMints <= MAX_SUPPLY,
"New mint exceeds maximum supply"
);
require(
totalSupply() + numMints <= MAX_SUPPLY - MAX_RESERVE + _reserved,
"New mint exceeds maximum available supply"
);
require(numMints <= MAX_MULTIMINT, "Exceeds max mints per transaction");
_mint(msg.sender, numMints);
}
function mintReserveToAddress(uint256 numMints, address recipient)
external
onlyOwner
{
require(
totalSupply() + numMints <= MAX_SUPPLY,
"New mint exceeds maximum supply"
);
require(
_reserved + numMints <= MAX_RESERVE,
"New mint exceeds reserve supply"
);
_reserved += numMints;
_mint(recipient, numMints);
}
function mintReserve(uint256 numMints) external onlyOwner {
require(
totalSupply() + numMints <= MAX_SUPPLY,
"New mint exceeds maximum supply"
);
require(
_reserved + numMints <= MAX_RESERVE,
"New mint exceeds reserve supply"
);
_reserved += numMints;
_mint(msg.sender, numMints);
}
function setCanvasSize(uint256 newSize) external onlyOwner {
require(!_canvasLocked, "Canvas size locked");
require(newSize < type(uint16).max, "Value too large");
_canvasSize = uint16(newSize);
}
function lockCanvasSize() external onlyOwner {
_canvasLocked = true;
}
function flipSaleState() external onlyOwner {
_status = !_status;
}
function setContractURI(string memory __contractURI) external onlyOwner {
_contractURI = __contractURI;
}
function _startTokenId() internal view virtual override returns (uint256) {
return 1;
}
function status() public view override returns (bool) {
return _status;
}
function contractURI() public view override returns (string memory) {
return _contractURI;
}
function reserved() public view override returns (uint256) {
return _reserved;
}
function price() public pure override returns (uint256) {
return PRICE;
}
function tokenURI(uint256 tokenId)
public
view
override
returns (string memory)
{
require(_exists(tokenId), "Query for nonexistant token");
return buildURI(tokenId);
}
}
文件 18 的 18:TreasureMetadata.sol
pragma solidity ^0.8.13;
import "@openzeppelin/contracts/utils/Strings.sol";
import "@openzeppelin/contracts/utils/Base64.sol";
contract TreasureMetadata {
using Strings for uint256;
mapping(string => Item) private _items;
struct Item {
string[] title;
uint32[] weight;
uint8[][] extra;
uint8[][] material;
}
struct Trait {
string title;
string attributeStr;
}
uint16 internal _canvasSize = 700;
bool internal _canvasLocked = false;
uint32[] private _numItemWts = [
50747683,
182949180,
472256061,
991823020,
1714634502,
2537383120,
3260194602,
3779761561,
4069068442,
4201269939,
4252017622
];
uint32[] private _numModWts = [
1308313,
107608754,
851711838,
3187704904,
4252017622
];
uint32[] private _itemCatWts = [
285240819,
646615385,
1644697520,
2322600746,
3918280648,
4185270226,
4252017621
];
constructor(
Item memory __head,
Item memory __torso,
Item memory __footwear,
Item memory __bottoms,
Item memory __weapon,
Item memory __shield,
Item memory __amulet,
Item memory __possessive,
Item memory __extra,
Item memory __material,
Item memory __tail
) {
_verifyItem(__head);
_verifyItem(__torso);
_verifyItem(__footwear);
_verifyItem(__bottoms);
_verifyItem(__weapon);
_verifyItem(__shield);
_verifyItem(__amulet);
_verifyItem(__possessive);
_verifyItem(__extra);
_verifyItem(__material);
_verifyItem(__tail);
_items["HEAD"] = __head;
_items["TORSO"] = __torso;
_items["FOOTWEAR"] = __footwear;
_items["BOTTOMS"] = __bottoms;
_items["WEAPON"] = __weapon;
_items["SHIELD"] = __shield;
_items["AMULET"] = __amulet;
_items["POSSESSIVE"] = __possessive;
_items["EXTRA"] = __extra;
_items["MATERIAL"] = __material;
_items["TAIL"] = __tail;
}
function buildURI(uint256 tokenId) internal view returns (string memory) {
Trait[] memory traits = _buildTraits(tokenId);
string[] memory parts = new string[](traits.length * 2 + 1);
parts[0] = string(
abi.encodePacked(
'<svg xmlns="http://www.w3.org/2000/svg" preserveAspectRatio="xMinYMin meet" viewBox="0 0 ',
(uint256(_canvasSize)).toString(),
" ",
(uint256(_canvasSize)).toString(),
'"><style>.base { fill: black; font-family: aleo; font-size: 19px; }</style><style>.title { fill: black; font-family: aleo; font-size: 28px; font-style: bold; }</style><rect width="100%" height="100%" fill="#FF8F00" /><text x="34" y="34" class="base">'
)
);
for (uint256 i = 1; i < traits.length; i++) {
parts[i * 2 - 1] = traits[i - 1].title;
parts[i * 2] = string(
abi.encodePacked(
'</text><text x="34" y="',
uint256(34 + i * 34).toString(),
'" class="base">'
)
);
}
parts[parts.length - 2] = traits[traits.length - 1].title;
parts[parts.length - 1] = string(
abi.encodePacked(
'</text><text x="',
(uint256(_canvasSize - 330)).toString(),
'" y="',
(uint256(_canvasSize - 30)).toString(),
'" class="title">Treasure. (For Warriors)</text></svg>'
)
);
string memory output = "";
for (uint256 i = 0; i < parts.length; i++) {
output = string(abi.encodePacked(output, parts[i]));
}
string memory attributes = "[";
for (uint256 i = 0; i < traits.length - 1; i++) {
attributes = string(
abi.encodePacked(attributes, traits[i].attributeStr, ",")
);
}
attributes = string(
abi.encodePacked(attributes, traits[traits.length - 1].attributeStr)
);
string memory json = Base64.encode(
bytes(
string(
abi.encodePacked(
'{"name": "Chest #',
tokenId.toString(),
'", "attributes": ',
attributes,
'], "description": "Treasure is randomized battle gear generated and stored on chain. Each treasure chest contains a variety of gear that warriors will use in battle. Ranging from armour, to weapons and survival gear. Feel free to use your treasure in any way you want.", "image": "data:image/svg+xml;base64,',
Base64.encode(bytes(output)),
'"}'
)
)
)
);
output = string(
abi.encodePacked("data:application/json;base64,", json)
);
return output;
}
function _buildTraits(uint256 tokenId)
private
view
returns (Trait[] memory)
{
uint256 numItems = _weightedRandom(
_numItemWts,
random(0, "ITEMS", tokenId),
0
) + 8;
uint256[] memory mains = getMains(tokenId, numItems);
require(mains.length == numItems, "Main items mismatch");
Trait[] memory traits = new Trait[](numItems);
for (uint256 i = 0; i < numItems; i++) {
if (mains[i] == 0) {
traits[i] = _buildTrait(getHead(tokenId, i), "Head");
} else if (mains[i] == 1) {
traits[i] = _buildTrait(getTorso(tokenId, i), "Torso");
} else if (mains[i] == 2) {
traits[i] = _buildTrait(getFootwear(tokenId, i), "Footwear");
} else if (mains[i] == 3) {
traits[i] = _buildTrait(getBottoms(tokenId, i), "Bottoms");
} else if (mains[i] == 4) {
traits[i] = _buildTrait(getWeapon(tokenId, i), "Weapon");
} else if (mains[i] == 5) {
traits[i] = _buildTrait(getShield(tokenId, i), "Shield");
} else {
traits[i] = _buildTrait(getAmulet(tokenId, i), "Amulet");
}
}
return traits;
}
function getHead(uint256 tokenId, uint256 index)
private
view
returns (string memory)
{
return compileMods(tokenId, index, "HEAD");
}
function getTorso(uint256 tokenId, uint256 index)
private
view
returns (string memory)
{
return compileMods(tokenId, index, "TORSO");
}
function getBottoms(uint256 tokenId, uint256 index)
private
view
returns (string memory)
{
return compileMods(tokenId, index, "BOTTOMS");
}
function getFootwear(uint256 tokenId, uint256 index)
private
view
returns (string memory)
{
return compileMods(tokenId, index, "FOOTWEAR");
}
function getWeapon(uint256 tokenId, uint256 index)
private
view
returns (string memory)
{
return compileMods(tokenId, index, "WEAPON");
}
function getShield(uint256 tokenId, uint256 index)
private
view
returns (string memory)
{
return compileMods(tokenId, index, "SHIELD");
}
function getAmulet(uint256 tokenId, uint256 index)
private
view
returns (string memory)
{
return compileMods(tokenId, index, "AMULET");
}
function compileMods(
uint256 tokenId,
uint256 index,
string memory category
) private view returns (string memory) {
uint256 numItems = _weightedRandom(
_numItemWts,
random(0, "ITEMS", tokenId),
0
) + 8;
uint256 mainSeed = random(index, category, tokenId);
uint256 possSeed = random(index, "POSSESSIVE", tokenId);
uint256 extraSeed = random(index, "EXTRA", tokenId);
uint256 matSeed = random(index, "MATERIAL", tokenId);
uint256 tailSeed = random(index, "TAIL", tokenId);
uint256 mainId = _weightedRandom(
_items[category].weight,
mainSeed,
numItems
);
string memory mainItem = _items[category].title[mainId];
uint256[] memory mods = getMods(category, tokenId, index);
if (mods.length == 0) {
return mainItem;
}
string[] memory parts = new string[](5);
parts[3] = mainItem;
for (uint256 i = 0; i < mods.length; i++) {
if (mods[i] == 7) {
parts[0] = string(
abi.encodePacked(
(
_items["POSSESSIVE"].title[
(
_weightedRandom(
_items["POSSESSIVE"].weight,
possSeed,
numItems
)
)
]
),
" "
)
);
} else if (mods[i] == 8) {
Item memory temp = getSelective(category, "EXTRA", mainId);
parts[1] = string(
abi.encodePacked(
(
temp.title[
(
_weightedRandom(
cumWts(temp.weight),
extraSeed,
numItems
)
)
]
),
" "
)
);
} else if (mods[i] == 9) {
Item memory temp = getSelective(category, "MATERIAL", mainId);
parts[2] = string(
abi.encodePacked(
(
temp.title[
(
_weightedRandom(
cumWts(temp.weight),
matSeed,
numItems
)
)
]
),
" "
)
);
} else if (mods[i] == 10) {
parts[4] = string(
abi.encodePacked(
" ",
(
_items["TAIL"].title[
(
_weightedRandom(
_items["TAIL"].weight,
tailSeed,
numItems
)
)
]
)
)
);
}
}
string memory fin = "";
for (uint256 i = 0; i < parts.length; i++) {
if (bytes(parts[i]).length > 0) {
fin = string(abi.encodePacked(fin, parts[i]));
}
}
return fin;
}
function getSelective(
string memory category,
string memory select,
uint256 index
) private view returns (Item memory) {
uint8[] memory indices = eqStr(select, "EXTRA")
? _items[category].extra[index]
: _items[category].material[index];
Item memory item = Item({
title: new string[](indices.length),
weight: new uint32[](indices.length),
extra: new uint8[][](0),
material: new uint8[][](0)
});
for (uint256 i = 0; i < indices.length; i++) {
uint8 id = indices[i];
item.title[i] = _items[select].title[id];
item.weight[i] = _items[select].weight[id];
}
return item;
}
function getMods(
string memory category,
uint256 tokenId,
uint256 index
) private view returns (uint256[] memory) {
uint256 numMods = _weightedRandom(
_numModWts,
random(index, "MODS", tokenId),
0
);
uint256[] memory mods = new uint256[](numMods);
uint32[] memory temp = new uint32[](4);
temp[0] = uint32(_items["POSSESSIVE"].weight.length * (10**6));
temp[1] = uint32(_items[category].extra.length * (10**6));
temp[2] = uint32(_items[category].material.length * (10**6));
temp[3] = uint32(_items["TAIL"].weight.length * (10**6));
for (uint256 i = 0; i < numMods; i++) {
uint256 s = random(i + 1, "MODIFIER", tokenId);
uint256 chosen = _weightedRandom(cumWts(temp), s, 0);
mods[i] = (chosen + 7);
delete temp[chosen];
}
return mods;
}
function getMains(uint256 tokenId, uint256 numItems)
private
view
returns (uint256[] memory)
{
uint256[] memory mains = new uint256[](numItems);
for (uint256 i = 0; i < numItems; i++) {
uint256 chosen = _weightedRandom(
_itemCatWts,
random(i + 1, "MAINS", tokenId),
0
);
mains[i] = chosen;
}
return mains;
}
function _buildTrait(string memory itemTitle, string memory traitType)
private
pure
returns (Trait memory)
{
string memory attrStr = string(
abi.encodePacked(
'{"trait_type": "',
traitType,
'","value": "',
itemTitle,
'"}'
)
);
return Trait({title: itemTitle, attributeStr: attrStr});
}
function random(
uint256 index,
string memory prefix,
uint256 tokenId
) private pure returns (uint256) {
return
uint256(
keccak256(
abi.encodePacked(
string(
abi.encodePacked(
index.toString(),
prefix,
tokenId.toString()
)
)
)
)
);
}
function _weightedRandom(
uint32[] memory weights,
uint256 seed,
uint256 _n
) private pure returns (uint256) {
_n = (_n > 18 || _n < 8) ? 18 : _n;
for (uint256 i = 0; i < weights.length; i++) {}
uint256 cumWt = weights[weights.length - 1];
uint256 toAdd = ((cumWt / 13**2) * ((18 - _n)**2)) >> 15;
uint256 target = seed % (cumWt + toAdd * weights.length);
for (uint256 i = 0; i < weights.length; i++) {
if (target < (weights[i] + (toAdd * (i + 1)))) {
return i;
}
}
require(false, "ERROR");
}
function eqStr(string memory str1, string memory str2)
private
pure
returns (bool)
{
return (
(keccak256(abi.encodePacked((str1))) ==
keccak256(abi.encodePacked((str2))))
);
}
function _verifyItem(Item memory _item) private pure {
require(
_item.title.length > 0 &&
_item.title.length == _item.weight.length &&
((_item.extra.length == _item.title.length &&
_item.material.length == _item.title.length) ||
(_item.extra.length == 0 && _item.material.length == 0))
);
}
function cumWts(uint32[] memory arr)
private
pure
returns (uint32[] memory)
{
uint32 total = 0;
uint32[] memory cums = new uint32[](arr.length);
for (uint256 i = 0; i < arr.length; i++) {
require(total + arr[i] < type(uint32).max, "Too Big");
total += arr[i];
cums[i] = total;
}
return cums;
}
}
{
"compilationTarget": {
"contracts/Treasure.sol": "Treasure"
},
"evmVersion": "london",
"libraries": {},
"metadata": {
"bytecodeHash": "ipfs"
},
"optimizer": {
"enabled": true,
"runs": 200
},
"remappings": []
}
[{"inputs":[{"components":[{"internalType":"string[]","name":"title","type":"string[]"},{"internalType":"uint32[]","name":"weight","type":"uint32[]"},{"internalType":"uint8[][]","name":"extra","type":"uint8[][]"},{"internalType":"uint8[][]","name":"material","type":"uint8[][]"}],"internalType":"struct TreasureMetadata.Item","name":"__head","type":"tuple"},{"components":[{"internalType":"string[]","name":"title","type":"string[]"},{"internalType":"uint32[]","name":"weight","type":"uint32[]"},{"internalType":"uint8[][]","name":"extra","type":"uint8[][]"},{"internalType":"uint8[][]","name":"material","type":"uint8[][]"}],"internalType":"struct TreasureMetadata.Item","name":"__torso","type":"tuple"},{"components":[{"internalType":"string[]","name":"title","type":"string[]"},{"internalType":"uint32[]","name":"weight","type":"uint32[]"},{"internalType":"uint8[][]","name":"extra","type":"uint8[][]"},{"internalType":"uint8[][]","name":"material","type":"uint8[][]"}],"internalType":"struct TreasureMetadata.Item","name":"__footwear","type":"tuple"},{"components":[{"internalType":"string[]","name":"title","type":"string[]"},{"internalType":"uint32[]","name":"weight","type":"uint32[]"},{"internalType":"uint8[][]","name":"extra","type":"uint8[][]"},{"internalType":"uint8[][]","name":"material","type":"uint8[][]"}],"internalType":"struct TreasureMetadata.Item","name":"__bottoms","type":"tuple"},{"components":[{"internalType":"string[]","name":"title","type":"string[]"},{"internalType":"uint32[]","name":"weight","type":"uint32[]"},{"internalType":"uint8[][]","name":"extra","type":"uint8[][]"},{"internalType":"uint8[][]","name":"material","type":"uint8[][]"}],"internalType":"struct TreasureMetadata.Item","name":"__weapon","type":"tuple"},{"components":[{"internalType":"string[]","name":"title","type":"string[]"},{"internalType":"uint32[]","name":"weight","type":"uint32[]"},{"internalType":"uint8[][]","name":"extra","type":"uint8[][]"},{"internalType":"uint8[][]","name":"material","type":"uint8[][]"}],"internalType":"struct TreasureMetadata.Item","name":"__shield","type":"tuple"},{"components":[{"internalType":"string[]","name":"title","type":"string[]"},{"internalType":"uint32[]","name":"weight","type":"uint32[]"},{"internalType":"uint8[][]","name":"extra","type":"uint8[][]"},{"internalType":"uint8[][]","name":"material","type":"uint8[][]"}],"internalType":"struct TreasureMetadata.Item","name":"__amulet","type":"tuple"},{"components":[{"internalType":"string[]","name":"title","type":"string[]"},{"internalType":"uint32[]","name":"weight","type":"uint32[]"},{"internalType":"uint8[][]","name":"extra","type":"uint8[][]"},{"internalType":"uint8[][]","name":"material","type":"uint8[][]"}],"internalType":"struct TreasureMetadata.Item","name":"__possessive","type":"tuple"},{"components":[{"internalType":"string[]","name":"title","type":"string[]"},{"internalType":"uint32[]","name":"weight","type":"uint32[]"},{"internalType":"uint8[][]","name":"extra","type":"uint8[][]"},{"internalType":"uint8[][]","name":"material","type":"uint8[][]"}],"internalType":"struct TreasureMetadata.Item","name":"__extra","type":"tuple"},{"components":[{"internalType":"string[]","name":"title","type":"string[]"},{"internalType":"uint32[]","name":"weight","type":"uint32[]"},{"internalType":"uint8[][]","name":"extra","type":"uint8[][]"},{"internalType":"uint8[][]","name":"material","type":"uint8[][]"}],"internalType":"struct TreasureMetadata.Item","name":"__material","type":"tuple"},{"components":[{"internalType":"string[]","name":"title","type":"string[]"},{"internalType":"uint32[]","name":"weight","type":"uint32[]"},{"internalType":"uint8[][]","name":"extra","type":"uint8[][]"},{"internalType":"uint8[][]","name":"material","type":"uint8[][]"}],"internalType":"struct TreasureMetadata.Item","name":"__tail","type":"tuple"}],"stateMutability":"nonpayable","type":"constructor"},{"inputs":[],"name":"ApprovalCallerNotOwnerNorApproved","type":"error"},{"inputs":[],"name":"ApprovalQueryForNonexistentToken","type":"error"},{"inputs":[],"name":"ApprovalToCurrentOwner","type":"error"},{"inputs":[],"name":"ApproveToCaller","type":"error"},{"inputs":[],"name":"BalanceQueryForZeroAddress","type":"error"},{"inputs":[],"name":"MintToZeroAddress","type":"error"},{"inputs":[],"name":"MintZeroQuantity","type":"error"},{"inputs":[],"name":"OwnerQueryForNonexistentToken","type":"error"},{"inputs":[],"name":"TransferCallerNotOwnerNorApproved","type":"error"},{"inputs":[],"name":"TransferFromIncorrectOwner","type":"error"},{"inputs":[],"name":"TransferToNonERC721ReceiverImplementer","type":"error"},{"inputs":[],"name":"TransferToZeroAddress","type":"error"},{"inputs":[],"name":"URIQueryForNonexistentToken","type":"error"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"owner","type":"address"},{"indexed":true,"internalType":"address","name":"approved","type":"address"},{"indexed":true,"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"Approval","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"owner","type":"address"},{"indexed":true,"internalType":"address","name":"operator","type":"address"},{"indexed":false,"internalType":"bool","name":"approved","type":"bool"}],"name":"ApprovalForAll","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"previousOwner","type":"address"},{"indexed":true,"internalType":"address","name":"newOwner","type":"address"}],"name":"OwnershipTransferred","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"account","type":"address"},{"indexed":false,"internalType":"uint256","name":"shares","type":"uint256"}],"name":"PayeeAdded","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"from","type":"address"},{"indexed":false,"internalType":"uint256","name":"amount","type":"uint256"}],"name":"PaymentReceived","type":"event"},{"anonymous":false,"inputs":[{"indexed":false,"internalType":"address","name":"to","type":"address"},{"indexed":false,"internalType":"uint256","name":"amount","type":"uint256"}],"name":"PaymentReleased","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"from","type":"address"},{"indexed":true,"internalType":"address","name":"to","type":"address"},{"indexed":true,"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"Transfer","type":"event"},{"inputs":[{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"approve","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"}],"name":"balanceOf","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"contractURI","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"flipSaleState","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"getApproved","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"owner","type":"address"},{"internalType":"address","name":"operator","type":"address"}],"name":"isApprovedForAll","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"lockCanvasSize","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"numMints","type":"uint256"}],"name":"mintReserve","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"numMints","type":"uint256"},{"internalType":"address","name":"recipient","type":"address"}],"name":"mintReserveToAddress","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"name","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"owner","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"ownerOf","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"index","type":"uint256"}],"name":"payee","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"numMints","type":"uint256"}],"name":"plunder","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[],"name":"price","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"pure","type":"function"},{"inputs":[{"internalType":"address payable","name":"account","type":"address"}],"name":"release","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"account","type":"address"}],"name":"released","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"renounceOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"reserved","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"from","type":"address"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"safeTransferFrom","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"from","type":"address"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"},{"internalType":"bytes","name":"_data","type":"bytes"}],"name":"safeTransferFrom","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"operator","type":"address"},{"internalType":"bool","name":"approved","type":"bool"}],"name":"setApprovalForAll","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint256","name":"newSize","type":"uint256"}],"name":"setCanvasSize","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"string","name":"__contractURI","type":"string"}],"name":"setContractURI","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"account","type":"address"}],"name":"shares","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"status","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes4","name":"interfaceId","type":"bytes4"}],"name":"supportsInterface","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"symbol","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"tokenURI","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"totalReleased","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"totalShares","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"totalSupply","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"from","type":"address"},{"internalType":"address","name":"to","type":"address"},{"internalType":"uint256","name":"tokenId","type":"uint256"}],"name":"transferFrom","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"address","name":"newOwner","type":"address"}],"name":"transferOwnership","outputs":[],"stateMutability":"nonpayable","type":"function"},{"stateMutability":"payable","type":"receive"}]