Blockwell

Neolastics

About

Stats

Public Functions 21
Event Types 5
Code Size 60,830 bytes

Library Use

Uses SafeMath for uint256.
Uses Address for address.
Uses EnumerableSet for EnumerableSet.UintSet.
Uses EnumerableMap for EnumerableMap.UintToAddressMap.
Uses Strings for uint256.

Approval Event

Parameters help
owner
address help
approved
address help
tokenId
uint256 help

ApprovalForAll Event

Parameters help
owner
address help
operator
address help
approved
bool help

Burned Event

Parameters help
tokenId
uint256 help
owner
address help
supplyAfterBurn
uint256 help

Minted Event

Parameters help
tokenId
uint256 help
totalEverMinted
uint256 help
timestamp
uint256 help
to
address help
supplyAfterMint
uint256 help

Transfer Event

Parameters help
from
address help
to
address help
tokenId
uint256 help

Functions Expand All Collapse All

supportsInterface keyboard_arrow_up

Parameters help

Name Type
interfaceId
bytes4 help

Properties

Visibility help public
Mutability help view
Source Code
    function supportsInterface(bytes4 interfaceId) public view override returns (bool) {
        return _supportedInterfaces[interfaceId];
    }

mint keyboard_arrow_up

Parameters help

Name Type
to
address help

Properties

Visibility help public
Mutability help transaction
Source Code
    function mint(address to) public virtual returns (uint256 newTokenId) {
        require(msg.sender == curve, "NEOLASTICS: Minter is not the curve");

        /*
        Neolastic generative art takes first 9 bytes of 32 to calculate colours for the 9 tiles.
        Thus: you *can* get duplicates. But they are rare.
        You can predict totalEverMinted + timestamp to *some* extent
        but hard to do so, unless explicitly manipulated by miners.
        The minter's address is used as additional 'salt'.
        Thus sufficiently "psuedo-random" to ensure that it's unreasonable to manipulate.
        */
        bytes32 hashed = keccak256(abi.encodePacked(totalEverMinted, block.timestamp, to));
        uint256 tokenId = uint(hashed);

        _mint(to, tokenId);

        // this can overflow, and should overflow (since by the time it overflows, timestamp will change)
        // but practically impossible to overflow.
        // could theoretically mint a duplicate if it overflows in one block, but practically impossible with economic constraints.
        totalEverMinted +=1; // for unique hashes per block

        emit Minted(tokenId, totalEverMinted, block.timestamp, to, totalSupply());

        return tokenId;
    }

generateSVGofTokenById keyboard_arrow_up

Parameters help

Name Type
_tokenId
uint256 help

Properties

Visibility help public
Mutability help view
Source Code
    function generateSVGofTokenById(uint256 _tokenId) public virtual view returns (string memory) {
        return generateSVGFromHash(bytes32(_tokenId));
    }

generateSVGFromHash keyboard_arrow_up

Parameters help

Name Type
_hash
bytes32 help

Properties

Visibility help public
Mutability help view
Source Code
    function generateSVGFromHash(bytes32 _hash) public virtual view returns (string memory) {
        bytes memory bhash = abi.encodePacked(_hash);

        // tile example
        // <rect x=0 y=0 width="100" height="100" style='fill:#fac901; strokeWidth:3; stroke:black'/>

        /*
        Each byte is a number between 0-255. If divided by 51, you get a number between 0-5.
        Most of the time it will be 0-4, but 1/256 chance it is 5. Which is rare. Green.

        Tiles are drawn from top-bottom, then left to right
        1 4 7
        2 5 8
        3 6 9
        */
        string memory svg = string(abi.encodePacked(
            "<svg width='300' height='300'>",
            string(abi.encodePacked("<rect x='0' y='0' width='100' height='100' style='fill:",palette[toUint8(bhash,0)/51],";stroke-width:3;stroke:black'/>")), // tile 1
            string(abi.encodePacked("<rect x='0' y='100' width='100' height='100' style='fill:",palette[toUint8(bhash,1)/51],";stroke-width:3;stroke:black'/>")), // tile 2
            string(abi.encodePacked("<rect x='0' y='200' width='100' height='100' style='fill:",palette[toUint8(bhash,2)/51],";stroke-width:3;stroke:black'/>")), // tile 3
            string(abi.encodePacked("<rect x='100' y='0' width='100' height='100' style='fill:",palette[toUint8(bhash,3)/51],";stroke-width:3;stroke:black'/>")), // tile 4
            string(abi.encodePacked("<rect x='100' y='100' width='100' height='100' style='fill:",palette[toUint8(bhash,4)/51],";stroke-width:3;stroke:black'/>")), // tile 5
            string(abi.encodePacked("<rect x='100' y='200' width='100' height='100' style='fill:",palette[toUint8(bhash,5)/51],";stroke-width:3;stroke:black'/>")), // tile 6
            string(abi.encodePacked("<rect x='200' y='0' width='100' height='100' style='fill:",palette[toUint8(bhash,6)/51],";stroke-width:3;stroke:black'/>")), // tile 7
            string(abi.encodePacked("<rect x='200' y='100' width='100' height='100' style='fill:",palette[toUint8(bhash,7)/51],";stroke-width:3;stroke:black'/>")), // tile 8
            string(abi.encodePacked("<rect x='200' y='200' width='100' height='100' style='fill:",palette[toUint8(bhash,8)/51],";stroke-width:3;stroke:black'/>")), // tile 9
            "</svg>"
        ));

        return svg;
    }

burn keyboard_arrow_up

Parameters help

Name Type
burner
address help
tokenId
uint256 help

Properties

Visibility help public
Mutability help transaction
Source Code
    function burn(address burner, uint256 tokenId) public virtual {
        require(msg.sender == curve, "NEOLASTICS: Burner is not the curve"); // only curve can burn it
        require(burner == ownerOf(tokenId), "NEOLASTICS: Not the correct owner");

        // checking if token exists in the _burn function (don't need to check here)

        _burn(tokenId);

        emit Burned(tokenId, burner, totalSupply());
    }

balanceOf keyboard_arrow_up

Parameters help

Name Type
owner
address help

Properties

Visibility help public
Mutability help view

Requirements help

Source Code
    function balanceOf(address owner) public view override returns (uint256) {
        require(owner != address(0), "ERC721: balance query for the zero address");

        return _holderTokens[owner].length();
    }

ownerOf keyboard_arrow_up

Parameters help

Name Type
tokenId
uint256 help

Properties

Visibility help public
Mutability help view
Source Code
    function ownerOf(uint256 tokenId) public view override returns (address) {
        return _tokenOwners.get(tokenId, "ERC721: owner query for nonexistent token");
    }

name keyboard_arrow_up

Parameters help

This function has no parameters.

Properties

Visibility help public
Mutability help view
Source Code
    function name() public view override returns (string memory) {
        return _name;
    }

symbol keyboard_arrow_up

Parameters help

This function has no parameters.

Properties

Visibility help public
Mutability help view
Source Code
    function symbol() public view override returns (string memory) {
        return _symbol;
    }

tokenURI keyboard_arrow_up

Parameters help

Name Type
tokenId
uint256 help

Properties

Visibility help public
Mutability help view

Requirements help

null
Source Code
    function tokenURI(uint256 tokenId) public view override returns (string memory) {
        require(_exists(tokenId), "ERC721Metadata: URI query for nonexistent token");

        string memory _tokenURI = _tokenURIs[tokenId];

        // If there is no base URI, return the token URI.
        if (bytes(_baseURI).length == 0) {
            return _tokenURI;
        }
        // If both are set, concatenate the baseURI and tokenURI (via abi.encodePacked).
        if (bytes(_tokenURI).length > 0) {
            return string(abi.encodePacked(_baseURI, _tokenURI));
        }
        // If there is a baseURI but no tokenURI, concatenate the tokenID to the baseURI.
        return string(abi.encodePacked(_baseURI, tokenId.toString()));
    }

baseURI keyboard_arrow_up

Parameters help

This function has no parameters.

Properties

Visibility help public
Mutability help view
Source Code
    function baseURI() public view returns (string memory) {
        return _baseURI;
    }

tokenOfOwnerByIndex keyboard_arrow_up

Parameters help

Name Type
owner
address help
index
uint256 help

Properties

Visibility help public
Mutability help view
Source Code
    function tokenOfOwnerByIndex(address owner, uint256 index) public view override returns (uint256) {
        return _holderTokens[owner].at(index);
    }

totalSupply keyboard_arrow_up

Parameters help

This function has no parameters.

Properties

Visibility help public
Mutability help view
Source Code
    function totalSupply() public view override returns (uint256) {
        // _tokenOwners are indexed by tokenIds, so .length() returns the number of tokenIds
        return _tokenOwners.length();
    }

tokenByIndex keyboard_arrow_up

Parameters help

Name Type
index
uint256 help

Properties

Visibility help public
Mutability help view
Source Code
    function tokenByIndex(uint256 index) public view override returns (uint256) {
        (uint256 tokenId, ) = _tokenOwners.at(index);
        return tokenId;
    }

approve keyboard_arrow_up

Parameters help

Name Type
to
address help
tokenId
uint256 help

Properties

Visibility help public
Mutability help transaction
Source Code
    function approve(address to, uint256 tokenId) public virtual override {
        address owner = ownerOf(tokenId);
        require(to != owner, "ERC721: approval to current owner");

        require(msg.sender == owner || isApprovedForAll(owner, msg.sender),
            "ERC721: approve caller is not owner nor approved for all"
        );

        _approve(to, tokenId);
    }

getApproved keyboard_arrow_up

Parameters help

Name Type
tokenId
uint256 help

Properties

Visibility help public
Mutability help view

Requirements help

null
Source Code
    function getApproved(uint256 tokenId) public view override returns (address) {
        require(_exists(tokenId), "ERC721: approved query for nonexistent token");

        return _tokenApprovals[tokenId];
    }

setApprovalForAll keyboard_arrow_up

Parameters help

Name Type
operator
address help
approved
bool help

Properties

Visibility help public
Mutability help transaction
Source Code
    function setApprovalForAll(address operator, bool approved) public virtual override {
        require(operator != msg.sender, "ERC721: approve to caller");

        _operatorApprovals[msg.sender][operator] = approved;
        emit ApprovalForAll(msg.sender, operator, approved);
    }

isApprovedForAll keyboard_arrow_up

Parameters help

Name Type
owner
address help
operator
address help

Properties

Visibility help public
Mutability help view
Source Code
    function isApprovedForAll(address owner, address operator) public view override returns (bool) {
        return _operatorApprovals[owner][operator];
    }

transferFrom keyboard_arrow_up

Parameters help

Name Type
from
address help
to
address help
tokenId
uint256 help

Properties

Visibility help public
Mutability help transaction
Source Code
    function transferFrom(address from, address to, uint256 tokenId) public virtual override {
        //solhint-disable-next-line max-line-length
        require(_isApprovedOrOwner(msg.sender, tokenId), "ERC721: transfer caller is not owner nor approved");

        _transfer(from, to, tokenId);
    }

safeTransferFrom keyboard_arrow_up

Parameters help

Name Type
from
address help
to
address help
tokenId
uint256 help

Properties

Visibility help public
Mutability help transaction
Source Code
    function safeTransferFrom(address from, address to, uint256 tokenId) public virtual override {
        safeTransferFrom(from, to, tokenId, "");
    }

safeTransferFrom keyboard_arrow_up

Parameters help

Name Type
from
address help
to
address help
tokenId
uint256 help
_data
bytes help

Properties

Visibility help public
Mutability help transaction
Source Code
    function safeTransferFrom(address from, address to, uint256 tokenId, bytes memory _data) public virtual override {
        require(_isApprovedOrOwner(msg.sender, tokenId), "ERC721: transfer caller is not owner nor approved");
        _safeTransfer(from, to, tokenId, _data);
    }