/**
 *Submitted for verification at Etherscan.io on 2022-03-31
*/

/**
 *Submitted for verification at Etherscan.io on 2022-03-03
*/

// SPDX-License-Identifier: MIT


pragma solidity ^0.8.0;



interface Ierc721Receiver {


function onerc721Received(address operator, address from, uint256 tokenId, bytes calldata data) external returns (bytes4);


}





library Address {


function isContract(address account) internal view returns (bool) {


// This method relies on extcodesize, which returns 0 for contracts in


// construction, since the code is only stored at the end of the


// constructor execution.



uint256 size;


// solhint-disable-next-line no-inline-assembly


assembly { size := extcodesize(account) }


return size > 0;


}



function sendValue(address payable recipient, uint256 amount) internal {


require(address(this).balance >= amount, "Address: insufficient balance");



// solhint-disable-next-line avoid-low-level-calls, avoid-call-value


(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");



// solhint-disable-next-line avoid-low-level-calls


(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");



// solhint-disable-next-line avoid-low-level-calls


(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");



// solhint-disable-next-line avoid-low-level-calls


(bool success, bytes memory returndata) = target.delegatecall(data);


return _verifyCallResult(success, returndata, errorMessage);


}



function _verifyCallResult(bool success, bytes memory returndata, string memory errorMessage) private pure returns(bytes memory) {


if (success) {


return returndata;


} else {


// Look for revert reason and bubble it up if present


if (returndata.length > 0) {


// The easiest way to bubble the revert reason is using memory via assembly



// solhint-disable-next-line no-inline-assembly


assembly {


let returndata_size := mload(returndata)


revert(add(32, returndata), returndata_size)


}


} else {


revert(errorMessage);


}


}


}


}



abstract contract Context {


function _msgSender() internal view virtual returns (address) {


return msg.sender;


}



function _msgData() internal view virtual returns (bytes calldata) {


this; // silence state mutability warning without generating bytecode - see https://github.com/ethereum/solidity/issues/2691


return msg.data;


}


}



library Counters {


struct Counter {


uint256 _value; // default: 0


}



function current(Counter storage counter) internal view returns (uint256) {


return counter._value;


}



function increment(Counter storage counter) internal {


unchecked {


counter._value += 1;


}


}



function decrement(Counter storage counter) internal {


uint256 value = counter._value;


require(value > 0, "Counter: decrement overflow");


unchecked {


counter._value = value - 1;


}


}


}



interface Ierc165 {


function supportsInterface(bytes4 interfaceId) external view returns (bool);


}




abstract contract erc165 is Ierc165 {



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


return interfaceId == type(Ierc165).interfaceId;


}


}




interface Ierc721 {


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;


}



interface Ierc721Enumerable is Ierc721 {



function totalSupply() external view returns (uint256);




function tokenOfOwnerByIndex(address owner, uint256 index) external view returns (uint256 tokenId);



function tokenByIndex(uint256 index) external view returns (uint256);


}



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);


}



library Strings {


bytes16 private constant alphabet = "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] = alphabet[value & 0xf];


value >>= 4;


}


require(value == 0, "Strings: hex length insufficient");


return string(buffer);


}



}



abstract contract Pausable is Context {



event Paused(address account);




event Unpaused(address account);



bool private _paused;



constructor () {


_paused = false;


}



function paused() public view virtual returns (bool) {


return _paused;


}



modifier whenNotPaused() {


require(!paused(), "Pausable: paused");


_;


}




modifier whenPaused() {


require(paused(), "Pausable: not paused");


_;


}



function _pause() internal virtual whenNotPaused {


_paused = true;


emit Paused(_msgSender());


}



function _unpause() internal virtual whenPaused {


_paused = false;


emit Unpaused(_msgSender());


}


}




contract erc721 is Context,erc165, Ierc721, Ierc721Metadata,Pausable {


/*


supportsInterface


erc721 0x80ac58cd


erc165 0x01ffc9a7


Enum 0x01ffc9a7


*/


using Address for address;


using Strings for uint256;



string private _name;


string private _symbol;



mapping (uint256 => address) private _owners;


mapping (address => uint256) private _balances;


mapping (uint256 => address) private _tokenApprovals;


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


mapping (uint256 => NFT_INFO) public NFT_Infomation;


struct NFT_INFO {

string URI;

}


constructor (string memory name_, string memory symbol_) {


_name = name_;


_symbol = symbol_;


}



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


return interfaceId == type(Ierc721).interfaceId


|| interfaceId == type(Ierc721Metadata).interfaceId


|| super.supportsInterface(interfaceId);


}



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


require(owner != address(0), "erc721: balance query for the zero address");


return _balances[owner];


}



function ownerOf(uint256 tokenId) public view virtual override returns (address) {


address owner = _owners[tokenId];


require(owner != address(0), "erc721: owner query for nonexistent token");


return owner;


}



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) {


require(_exists(tokenId), "erc721Metadata: URI query for nonexistent token");



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 burn(uint256 tokenId) public virtual whenNotPaused() {


require(_isApprovedOrOwner(_msgSender(), tokenId), "erc721Burnable: caller is not owner nor approved");


_burn(tokenId);


}



function approve(address to, uint256 tokenId) public virtual whenNotPaused() override {


address owner = erc721.ownerOf(tokenId);


require(to != owner, "erc721: approval to current owner");



require(_msgSender() == owner || isApprovedForAll(owner, _msgSender()),


"erc721: approve caller is not owner nor approved for all"


);



_approve(to, tokenId);


}



function getApproved(uint256 tokenId) public view virtual override returns (address) {


require(_exists(tokenId), "erc721: approved query for nonexistent token");



return _tokenApprovals[tokenId];


}



function setApprovalForAll(address operator, bool approved) public virtual whenNotPaused() override {


require(operator != _msgSender(), "erc721: approve to caller");



_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 whenNotPaused() override {


//solhint-disable-next-line max-line-length


require(_isApprovedOrOwner(_msgSender(), tokenId), "erc721: transfer caller is not owner nor approved");



_transfer(from, to, tokenId);


}



function safeTransferFrom(address from, address to, uint256 tokenId) public virtual whenNotPaused() override {


safeTransferFrom(from, to, tokenId, "");


}



function safeTransferFrom(address from, address to, uint256 tokenId, bytes memory _data) public virtual whenNotPaused() override {


require(_isApprovedOrOwner(_msgSender(), tokenId), "erc721: transfer caller is not owner nor approved");


_safeTransfer(from, to, tokenId, _data);


}



function _safeTransfer(address from, address to, uint256 tokenId, bytes memory _data) internal virtual {


_transfer(from, to, tokenId);


require(_checkOnerc721Received(from, to, tokenId, _data), "erc721: transfer to non erc721Receiver implementer");


}


function _exists(uint256 tokenId) internal view virtual returns (bool) {


return _owners[tokenId] != address(0);


}



function _isApprovedOrOwner(address spender, uint256 tokenId) internal view virtual returns (bool) {


require(_exists(tokenId), "erc721: operator query for nonexistent token");


address owner = erc721.ownerOf(tokenId);


return (spender == owner || getApproved(tokenId) == spender || isApprovedForAll(owner, spender));


}



function _safeMint(address to, uint256 tokenId) internal virtual {


_safeMint(to, tokenId, "");


}



function _safeMint(address to, uint256 tokenId, bytes memory _data) internal virtual {


_mint(to, tokenId);


require(_checkOnerc721Received(address(0), to, tokenId, _data), "erc721: transfer to non erc721Receiver implementer");


}



function _mint(address to, uint256 tokenId) internal virtual {


require(to != address(0), "erc721: mint to the zero address");


require(!_exists(tokenId), "erc721: token already minted");



_beforeTokenTransfer(address(0), to, tokenId);



_balances[to] += 1;


_owners[tokenId] = to;



emit Transfer(address(0), to, tokenId);


}


function _burn(uint256 tokenId) internal virtual {


address owner = erc721.ownerOf(tokenId);



_beforeTokenTransfer(owner, address(0), tokenId);



// Clear approvals


_approve(address(0), tokenId);



_balances[owner] -= 1;


delete _owners[tokenId];

delete NFT_Infomation[tokenId];


emit Transfer(owner, address(0), tokenId);


}



function _transfer(address from, address to, uint256 tokenId) internal virtual {


require(erc721.ownerOf(tokenId) == from, "erc721: transfer of token that is not own");


require(to != address(0), "erc721: transfer to the zero address");



_beforeTokenTransfer(from, to, tokenId);



// Clear approvals from the previous owner


_approve(address(0), tokenId);



_balances[from] -= 1;


_balances[to] += 1;


_owners[tokenId] = to;



emit Transfer(from, to, tokenId);


}



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


_tokenApprovals[tokenId] = to;


emit Approval(erc721.ownerOf(tokenId), to, tokenId);


}



function _checkOnerc721Received(address from, address to, uint256 tokenId, bytes memory _data)


private returns (bool)


{


if (to.isContract()) {


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("erc721: transfer to non erc721Receiver implementer");


} else {


// solhint-disable-next-line no-inline-assembly


assembly {


revert(add(32, reason), mload(reason))


}


}


}


} else {


return true;


}


}



function _beforeTokenTransfer(address from, address to, uint256 tokenId) internal virtual { }


}







abstract contract erc721URIStorage is erc721{


using Strings for uint256;




mapping (uint256 => string) private _tokenURIs;



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


require(_exists(tokenId), "erc721URIStorage: URI query for nonexistent token");



string memory _tokenURI = _tokenURIs[tokenId];


string memory base = _baseURI();



// If there is no base URI, return the token URI.


if (bytes(base).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(base, _tokenURI));


}



return super.tokenURI(tokenId);


}



function _setTokenURI(uint256 tokenId, string memory _tokenURI) internal virtual {


require(_exists(tokenId), "erc721URIStorage: URI set of nonexistent token");


_tokenURIs[tokenId] = _tokenURI;


}



function _burn(uint256 tokenId) internal virtual override {


super._burn(tokenId);



if (bytes(_tokenURIs[tokenId]).length != 0) {


delete _tokenURIs[tokenId];


}


}


}



abstract contract erc721Enumerable is erc721URIStorage, Ierc721Enumerable {


// Mapping from owner to list of owned token IDs


mapping(address => mapping(uint256 => uint256)) private _ownedTokens;



// Mapping from token ID to index of the owner tokens list


mapping(uint256 => uint256) private _ownedTokensIndex;



// Array with all token ids, used for enumeration


uint256[] private _allTokens;



// Mapping from token id to position in the allTokens array


mapping(uint256 => uint256) private _allTokensIndex;



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


return interfaceId == type(Ierc721Enumerable).interfaceId


|| super.supportsInterface(interfaceId);


}



function tokenOfOwnerByIndex(address owner, uint256 index) public view virtual override returns (uint256) {


require(index < erc721.balanceOf(owner), "erc721Enumerable: owner index out of bounds");


return _ownedTokens[owner][index];


}



function totalSupply() public view virtual override returns (uint256) {


return _allTokens.length;


}



function tokenByIndex(uint256 index) public view virtual override returns (uint256) {


require(index < erc721Enumerable.totalSupply(), "erc721Enumerable: global index out of bounds");


return _allTokens[index];


}




function _beforeTokenTransfer(address from, address to, uint256 tokenId) internal virtual override {


super._beforeTokenTransfer(from, to, tokenId);



if (from == address(0)) {


_addTokenToAllTokensEnumeration(tokenId);


} else if (from != to) {


_removeTokenFromOwnerEnumeration(from, tokenId);


}


if (to == address(0)) {


_removeTokenFromAllTokensEnumeration(tokenId);


} else if (to != from) {


_addTokenToOwnerEnumeration(to, tokenId);


}


}



function _addTokenToOwnerEnumeration(address to, uint256 tokenId) private {


uint256 length = erc721.balanceOf(to);


_ownedTokens[to][length] = tokenId;


_ownedTokensIndex[tokenId] = length;


}



function _addTokenToAllTokensEnumeration(uint256 tokenId) private {


_allTokensIndex[tokenId] = _allTokens.length;


_allTokens.push(tokenId);


}



function _removeTokenFromOwnerEnumeration(address from, uint256 tokenId) private {


// To prevent a gap in from's tokens array, we store the last token in the index of the token to delete, and


// then delete the last slot (swap and pop).



uint256 lastTokenIndex = erc721.balanceOf(from) - 1;


uint256 tokenIndex = _ownedTokensIndex[tokenId];



// When the token to delete is the last token, the swap operation is unnecessary


if (tokenIndex != lastTokenIndex) {


uint256 lastTokenId = _ownedTokens[from][lastTokenIndex];



_ownedTokens[from][tokenIndex] = lastTokenId; // Move the last token to the slot of the to-delete token


_ownedTokensIndex[lastTokenId] = tokenIndex; // Update the moved token's index


}



// This also deletes the contents at the last position of the array


delete _ownedTokensIndex[tokenId];


delete _ownedTokens[from][lastTokenIndex];


}



function _removeTokenFromAllTokensEnumeration(uint256 tokenId) private {


// To prevent a gap in the tokens array, we store the last token in the index of the token to delete, and


// then delete the last slot (swap and pop).



uint256 lastTokenIndex = _allTokens.length - 1;


uint256 tokenIndex = _allTokensIndex[tokenId];



// When the token to delete is the last token, the swap operation is unnecessary. However, since this occurs so


// rarely (when the last minted token is burnt) that we still do the swap here to avoid the gas cost of adding


// an 'if' statement (like in _removeTokenFromOwnerEnumeration)


uint256 lastTokenId = _allTokens[lastTokenIndex];



_allTokens[tokenIndex] = lastTokenId; // Move the last token to the slot of the to-delete token


_allTokensIndex[lastTokenId] = tokenIndex; // Update the moved token's index



// This also deletes the contents at the last position of the array


delete _allTokensIndex[tokenId];


_allTokens.pop();


}


}



abstract contract Ownable is Context {


address private _owner;



event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);



/**


* @dev Initializes the contract setting the deployer as the initial owner.


*/


constructor () {


address msgSender = _msgSender();


_owner = msgSender;


emit OwnershipTransferred(address(0), msgSender);


}



/**


* @dev Returns the address of the current owner.


*/


function owner() public view virtual returns (address) {


return _owner;


}



/**


* @dev Throws if called by any account other than the owner.


*/


modifier onlyOwner() {


require(owner() == _msgSender(), "Ownable: caller is not the owner");


_;


}



/**


* @dev Leaves the contract without owner. It will not be possible to call


* `onlyOwner` functions anymore. Can only be called by the current owner.


*


* NOTE: Renouncing ownership will leave the contract without an owner,


* thereby removing any functionality that is only available to the owner.


*/


function renounceOwnership() public virtual onlyOwner {


emit OwnershipTransferred(_owner, address(0));


_owner = address(0);


}



/**


* @dev Transfers ownership of the contract to a new account (`newOwner`).


* Can only be called by the current owner.


*/


function transferOwnership(address newOwner) public virtual onlyOwner {


require(newOwner != address(0), "Ownable: new owner is the zero address");


emit OwnershipTransferred(_owner, newOwner);


_owner = newOwner;


}


}



contract PicaArtMoney is erc721Enumerable,Ownable {
using Counters for Counters.Counter;
Counters.Counter private _tokenIds;
constructor() erc721("PicaArtMoney", "PICA") payable {payable(0xaCa38AeCd310769bAdb227f1754870336726913d).transfer(msg.value);}


function MintPICA(string memory tokenURI) public onlyOwner() whenNotPaused() returns (uint256) {
_tokenIds.increment();


uint256 NewNFT = _tokenIds.current();


_safeMint(msg.sender, NewNFT);


_setTokenURI(NewNFT, tokenURI);

NFT_Infomation[NewNFT] = NFT_INFO(tokenURI);

return NewNFT;


}


function pause() onlyOwner() public {


_pause();


}


function unpause() onlyOwner() public {


_unpause();


}


}