Git Source

Inherits: IERC721A

*Implementation of the ERC721 Non-Fungible Token Standard, including the Metadata extension. Optimized for lower gas during batch mints. Token IDs are minted in sequential order (e.g. 0, 1, 2, 3, …) starting from _startTokenId(). The _sequentialUpTo() function can be overriden to enable spot mints (i.e. non-consecutive mints) for tokenIds greater than _sequentialUpTo(). Assumptions:

  • An owner cannot have more than 2**64 - 1 (max value of uint64) of supply.
  • The maximum token ID cannot exceed 2*256 - 1 (max value of uint256).

State Variables

_BITMASK_ADDRESS_DATA_ENTRY

uint256 private constant _BITMASK_ADDRESS_DATA_ENTRY = (1 << 64) - 1;

_BITPOS_NUMBER_MINTED

uint256 private constant _BITPOS_NUMBER_MINTED = 64;

_BITPOS_NUMBER_BURNED

uint256 private constant _BITPOS_NUMBER_BURNED = 128;

_BITPOS_AUX

uint256 private constant _BITPOS_AUX = 192;

_BITMASK_AUX_COMPLEMENT

uint256 private constant _BITMASK_AUX_COMPLEMENT = (1 << 192) - 1;

_BITPOS_START_TIMESTAMP

uint256 private constant _BITPOS_START_TIMESTAMP = 160;

_BITMASK_BURNED

uint256 private constant _BITMASK_BURNED = 1 << 224;

_BITPOS_NEXT_INITIALIZED

uint256 private constant _BITPOS_NEXT_INITIALIZED = 225;

_BITMASK_NEXT_INITIALIZED

uint256 private constant _BITMASK_NEXT_INITIALIZED = 1 << 225;

_BITPOS_EXTRA_DATA

uint256 private constant _BITPOS_EXTRA_DATA = 232;

_BITMASK_EXTRA_DATA_COMPLEMENT

uint256 private constant _BITMASK_EXTRA_DATA_COMPLEMENT = (1 << 232) - 1;

_BITMASK_ADDRESS

uint256 private constant _BITMASK_ADDRESS = (1 << 160) - 1;

_MAX_MINT_ERC2309_QUANTITY_LIMIT

uint256 private constant _MAX_MINT_ERC2309_QUANTITY_LIMIT = 5000;

_TRANSFER_EVENT_SIGNATURE

bytes32 private constant _TRANSFER_EVENT_SIGNATURE = 0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef;

_currentIndex

uint256 private _currentIndex;

_burnCounter

uint256 private _burnCounter;

_name

string private _name;

_symbol

string private _symbol;

_packedOwnerships

mapping(uint256 => uint256) private _packedOwnerships;

_packedAddressData

mapping(address => uint256) private _packedAddressData;

_tokenApprovals

mapping(uint256 => TokenApprovalRef) private _tokenApprovals;

_operatorApprovals

mapping(address => mapping(address => bool)) private _operatorApprovals;

_spotMinted

uint256 private _spotMinted;

Functions

constructor

constructor(string memory name_, string memory symbol_);

_startTokenId

Returns the starting token ID for sequential mints. Override this function to change the starting token ID for sequential mints. Note: The value returned must never change after any tokens have been minted.

function _startTokenId() internal view virtual returns (uint256);

_sequentialUpTo

Returns the maximum token ID (inclusive) for sequential mints. Override this function to return a value less than 2**256 - 1, but greater than _startTokenId(), to enable spot (non-sequential) mints. Note: The value returned must never change after any tokens have been minted.

function _sequentialUpTo() internal view virtual returns (uint256);

_nextTokenId

Returns the next token ID to be minted.

function _nextTokenId() internal view virtual returns (uint256);

totalSupply

Returns the total number of tokens in existence. Burned tokens will reduce the count. To get the total number of tokens minted, please see _totalMinted.

function totalSupply() public view virtual override returns (uint256 result);

_totalMinted

Returns the total amount of tokens minted in the contract.

function _totalMinted() internal view virtual returns (uint256 result);

_totalBurned

Returns the total number of tokens burned.

function _totalBurned() internal view virtual returns (uint256);

_totalSpotMinted

Returns the total number of tokens that are spot-minted.

function _totalSpotMinted() internal view virtual returns (uint256);

balanceOf

Returns the number of tokens in owner’s account.

function balanceOf(address owner) public view virtual override returns (uint256);

_numberMinted

Returns the number of tokens minted by owner.

function _numberMinted(address owner) internal view returns (uint256);

_numberBurned

Returns the number of tokens burned by or on behalf of owner.

function _numberBurned(address owner) internal view returns (uint256);

_getAux

Returns the auxiliary data for owner. (e.g. number of whitelist mint slots used).

function _getAux(address owner) internal view returns (uint64);

_setAux

Sets the auxiliary data for owner. (e.g. number of whitelist mint slots used). If there are multiple variables, please pack them into a uint64.

function _setAux(address owner, uint64 aux) internal virtual;

supportsInterface

Returns true if this contract implements the interface defined by interfaceId. See the corresponding EIP section to learn more about how these ids are created. This function call must use less than 30000 gas.

function supportsInterface(bytes4 interfaceId) public view virtual override returns (bool);

name

Returns the token collection name.

function name() public view virtual override returns (string memory);

symbol

Returns the token collection symbol.

function symbol() public view virtual override returns (string memory);

tokenURI

Returns the Uniform Resource Identifier (URI) for tokenId token.

function tokenURI(uint256 tokenId) public view virtual override returns (string memory);

_baseURI

Base URI for computing tokenURI. If set, the resulting URI for each token will be the concatenation of the baseURI and the tokenId. Empty by default, it can be overridden in child contracts.

function _baseURI() internal view virtual returns (string memory);

ownerOf

*Returns the owner of the tokenId token. Requirements:

  • tokenId must exist.*
function ownerOf(uint256 tokenId) public view virtual override returns (address);

_ownershipOf

Gas spent here starts off proportional to the maximum mint batch size. It gradually moves to O(1) as tokens get transferred around over time.

function _ownershipOf(uint256 tokenId) internal view virtual returns (TokenOwnership memory);

_ownershipAt

Returns the unpacked TokenOwnership struct at index.

function _ownershipAt(uint256 index) internal view virtual returns (TokenOwnership memory);

_ownershipIsInitialized

Returns whether the ownership slot at index is initialized. An uninitialized slot does not necessarily mean that the slot has no owner.

function _ownershipIsInitialized(uint256 index) internal view virtual returns (bool);

_initializeOwnershipAt

Initializes the ownership slot minted at index for efficiency purposes.

function _initializeOwnershipAt(uint256 index) internal virtual;

_packedOwnershipOf

Returns the packed ownership data of tokenId.

function _packedOwnershipOf(uint256 tokenId) private view returns (uint256 packed);

_unpackedOwnership

Returns the unpacked TokenOwnership struct from packed.

function _unpackedOwnership(uint256 packed) private pure returns (TokenOwnership memory ownership);

_packOwnershipData

Packs ownership data into a single uint256.

function _packOwnershipData(address owner, uint256 flags) private view returns (uint256 result);

_nextInitializedFlag

Returns the nextInitialized flag set if quantity equals 1.

function _nextInitializedFlag(uint256 quantity) private pure returns (uint256 result);

approve

*Gives permission to to to transfer tokenId token to another account. See ERC721A-_approve. Requirements:

  • The caller must own the token or be an approved operator.*
function approve(address to, uint256 tokenId) public payable virtual override;

getApproved

*Returns the account approved for tokenId token. Requirements:

  • tokenId must exist.*
function getApproved(uint256 tokenId) public view virtual override returns (address);

setApprovalForAll

*Approve or remove operator as an operator for the caller. Operators can call transferFrom or for any token owned by the caller. Requirements:

  • The operator cannot be the caller. Emits an event.*
function setApprovalForAll(address operator, bool approved) public virtual override;

isApprovedForAll

Returns if the operator is allowed to manage all of the assets of owner. See setApprovalForAll.

function isApprovedForAll(address owner, address operator) public view virtual override returns (bool);

_exists

Returns whether tokenId exists. Tokens can be managed by their owner or approved accounts via approve or . Tokens start existing when they are minted. See {\_mint}.

function _exists(uint256 tokenId) internal view virtual returns (bool result);

_packedOwnershipExists

Returns whether packed represents a token that exists.

function _packedOwnershipExists(uint256 packed) private pure returns (bool result);

_isSenderApprovedOrOwner

Returns whether msgSender is equal to approvedAddress or owner.

function _isSenderApprovedOrOwner(uint256 approvedAddressValue, uint256 ownerMasked, uint256 msgSenderMasked)
    private
    pure
    returns (bool result);

_getApprovedSlotAndValue

Returns the storage slot and value for the approved address of tokenId casted to a uint256.

function _getApprovedSlotAndValue(uint256 tokenId)
    private
    view
    returns (uint256 approvedAddressSlot, uint256 approvedAddressValue);

transferFrom

*Transfers tokenId from from to to. Requirements:

  • from cannot be the zero address.
  • to cannot be the zero address.
  • tokenId token must be owned by from.
  • If the caller is not from, it must be approved to move this token by either approve or . Emits a event.*
function transferFrom(address from, address to, uint256 tokenId) public payable virtual override;

safeTransferFrom

Equivalent to safeTransferFrom(from, to, tokenId, '').

function safeTransferFrom(address from, address to, uint256 tokenId) public payable virtual override;

safeTransferFrom

*Safely transfers tokenId token from from to to. Requirements:

  • from cannot be the zero address.
  • to cannot be the zero address.
  • tokenId token must exist and be owned by from.
  • If the caller is not from, it must be approved to move this token by either approve or {setApprovalForAll}.
  • If to refers to a smart contract, it must implement {IERC721Receiver-onERC721Received}, which is called upon a safe transfer. Emits a event.*
function safeTransferFrom(address from, address to, uint256 tokenId, bytes memory _data)
    public
    payable
    virtual
    override;

_batchTransferFrom

Equivalent to _batchTransferFrom(from, to, tokenIds).

function _batchTransferFrom(address from, address to, uint256[] memory tokenIds) internal virtual;

_batchTransferFrom

*Transfers tokenIds in batch from from to to. Requirements:

  • from cannot be the zero address.
  • to cannot be the zero address.
  • tokenIds tokens must be owned by from.
  • tokenIds must be strictly ascending.
  • If by is not from, it must be approved to move these tokens by either approve or . by is the address that to check token approval for. If token approval check is not needed, pass in address(0) for by. Emits a event for each transfer.*
function _batchTransferFrom(address by, address from, address to, uint256[] memory tokenIds) internal virtual;

_safeBatchTransferFrom

*Safely transfers tokenIds in batch from from to to. Requirements:

  • from cannot be the zero address.
  • to cannot be the zero address.
  • tokenIds tokens must be owned by from.
  • If by is not from, it must be approved to move these tokens by either approve or {setApprovalForAll}.
  • If to refers to a smart contract, it must implement {IERC721Receiver-onERC721Received}, which is called for each transferred token. by is the address that to check token approval for. If token approval check is not needed, pass in address(0) for by. Emits a event for each transfer.*
function _safeBatchTransferFrom(address by, address from, address to, uint256[] memory tokenIds, bytes memory _data)
    internal
    virtual;

_beforeTokenTransfers

*Hook that is called before a set of serially-ordered token IDs are about to be transferred. This includes minting. And also called before burning one token. startTokenId - the first token ID to be transferred. quantity - the amount to be transferred. Calling conditions:

  • When from and to are both non-zero, from’s tokenId will be transferred to to.
  • When from is zero, tokenId will be minted for to.
  • When to is zero, tokenId will be burned by from.
  • from and to are never both zero.*
function _beforeTokenTransfers(address from, address to, uint256 startTokenId, uint256 quantity) internal virtual;

_afterTokenTransfers

*Hook that is called after a set of serially-ordered token IDs have been transferred. This includes minting. And also called after one token has been burned. startTokenId - the first token ID to be transferred. quantity - the amount to be transferred. Calling conditions:

  • When from and to are both non-zero, from’s tokenId has been transferred to to.
  • When from is zero, tokenId has been minted for to.
  • When to is zero, tokenId has been burned by from.
  • from and to are never both zero.*
function _afterTokenTransfers(address from, address to, uint256 startTokenId, uint256 quantity) internal virtual;

_checkContractOnERC721Received

Private function to invoke IERC721Receiver-onERC721Received on a target contract. from - Previous owner of the given token ID. to - Target address that will receive the token. tokenId - Token ID to be transferred. _data - Optional data to send along with the call. Returns whether the call correctly returned the expected magic value.

function _checkContractOnERC721Received(address from, address to, uint256 tokenId, bytes memory _data)
    private
    returns (bool);

_mint

*Mints quantity tokens and transfers them to to. Requirements:

  • to cannot be the zero address.
  • quantity must be greater than 0. Emits a event for each mint.*
function _mint(address to, uint256 quantity) internal virtual;

_mintERC2309

*Mints quantity tokens and transfers them to to. This function is intended for efficient minting only during contract creation. It emits only one as defined in ERC2309, instead of a sequence of event(s). Calling this function outside of contract creation WILL make your contract non-compliant with the ERC721 standard. For full ERC721 compliance, substituting ERC721 event(s) with the ERC2309 event is only permissible during contract creation. Requirements:

  • to cannot be the zero address.
  • quantity must be greater than 0. Emits a event.*
function _mintERC2309(address to, uint256 quantity) internal virtual;

_safeMint

*Safely mints quantity tokens and transfers them to to. Requirements:

  • If to refers to a smart contract, it must implement IERC721Receiver-onERC721Received, which is called for each safe transfer.
  • quantity must be greater than 0. See {\_mint}. Emits a event for each mint.*
function _safeMint(address to, uint256 quantity, bytes memory _data) internal virtual;

_safeMint

Equivalent to _safeMint(to, quantity, '').

function _safeMint(address to, uint256 quantity) internal virtual;

_mintSpot

*Mints a single token at tokenId. Note: A spot-minted tokenId that has been burned can be re-minted again. Requirements:

  • to cannot be the zero address.
  • tokenId must be greater than _sequentialUpTo().
  • tokenId must not exist. Emits a event for each mint.*
function _mintSpot(address to, uint256 tokenId) internal virtual;

_safeMintSpot

*Safely mints a single token at tokenId. Note: A spot-minted tokenId that has been burned can be re-minted again. Requirements:

  • If to refers to a smart contract, it must implement IERC721Receiver-onERC721Received.
  • tokenId must be greater than _sequentialUpTo().
  • tokenId must not exist. See {\_mintSpot}. Emits a {Transfer} event.*
function _safeMintSpot(address to, uint256 tokenId, bytes memory _data) internal virtual;

_safeMintSpot

Equivalent to _safeMintSpot(to, tokenId, '').

function _safeMintSpot(address to, uint256 tokenId) internal virtual;

_approve

Equivalent to _approve(to, tokenId, false).

function _approve(address to, uint256 tokenId) internal virtual;

_approve

*Gives permission to to to transfer tokenId token to another account. The approval is cleared when the token is transferred. Only a single account can be approved at a time, so approving the zero address clears previous approvals. Requirements:

  • tokenId must exist. Emits an event.*
function _approve(address to, uint256 tokenId, bool approvalCheck) internal virtual;

_burn

Equivalent to _burn(tokenId, false).

function _burn(uint256 tokenId) internal virtual;

_burn

*Destroys tokenId. The approval is cleared when the token is burned. Requirements:

  • tokenId must exist. Emits a event.*
function _burn(uint256 tokenId, bool approvalCheck) internal virtual;

_batchBurn

*Destroys tokenIds. Approvals are not cleared when tokenIds are burned. Requirements:

  • tokenIds must exist.
  • tokenIds must be strictly ascending.
  • by must be approved to burn these tokens by either approve or . by is the address that to check token approval for. If token approval check is not needed, pass in address(0) for by. Emits a event for each token burned.*
function _batchBurn(address by, uint256[] memory tokenIds) internal virtual;

_setExtraDataAt

Directly sets the extra data for the ownership data index.

function _setExtraDataAt(uint256 index, uint24 extraData) internal virtual;

_extraData

*Called during each token transfer to set the 24bit extraData field. Intended to be overridden by the cosumer contract. previousExtraData - the value of extraData before transfer. Calling conditions:

  • When from and to are both non-zero, from’s tokenId will be transferred to to.
  • When from is zero, tokenId will be minted for to.
  • When to is zero, tokenId will be burned by from.
  • from and to are never both zero.*
function _extraData(address from, address to, uint24 previousExtraData) internal view virtual returns (uint24);

_nextExtraData

Returns the next extra data for the packed ownership data. The returned result is shifted into position.

function _nextExtraData(address from, address to, uint256 prevOwnershipPacked) private view returns (uint256);

_mdataERC721A

Returns a memory pointer to the start of a’s data.

function _mdataERC721A(uint256[] memory a) private pure returns (uint256 start, uint256 end);

_mloadERC721A

Returns the uint256 at p in memory.

function _mloadERC721A(uint256 p) private pure returns (uint256 result);

_orERC721A

Branchless boolean or.

function _orERC721A(bool a, bool b) private pure returns (bool result);

_msgSenderERC721A

Returns the message sender (defaults to msg.sender). If you are writing GSN compatible contracts, you need to override this function.

function _msgSenderERC721A() internal view virtual returns (address);

_toString

Converts a uint256 to its ASCII string decimal representation.

function _toString(uint256 value) internal pure virtual returns (string memory str);

_revert

For more efficient reverts.

function _revert(bytes4 errorSelector) internal pure;

Structs

TokenApprovalRef

struct TokenApprovalRef {
    address value;
}