contract Genesis is ERC721Enumerable, Ownable, ReentrancyGuard {
    /// @dev token id tracker
    uint256 public tokenIdTracker;

    // /// @dev Maximum elements
    // uint256 CAP = 333;

    /// baseTokenURI
    string public baseTokenURI;

    address public immutable nftOwner =
        0x3B0C7fb36cCf7bB203e5126B2192371Af91831BF;

    address public oldGenesis;

    // event Mint(address indexed to, uint256 amount);
    
    event Claim(uint256[] tokenIds);
    uint[] public tokenToOpenseaMap;

    event SetBaseTokenURI(string baseTokenURI);

    constructor(
        string memory _name,
        string memory _symbol,
        string memory _baseURI,
        address _oldGenesis,
        uint[] memory tokens
    ) ERC721(_name, _symbol) {
        setBaseURI(_baseURI);
        setOldGenesis(_oldGenesis);
        tokenToOpenseaMap = tokens;
    }

    /**
     * @dev Claim NFT
     */
    function claim(uint256[] memory _tokenIds) external nonReentrant {
        require(_tokenIds.length != 0, "genesis : invalid tokenId length");

        for (uint256 i = 0; i < _tokenIds.length; i++) {
            uint256 tokenId = _tokenIds[i];

            require(tokenId != 0, "genesis : invalid tokenId");

            uint256 count = IERC1155(oldGenesis).balanceOf(msg.sender, tokenToOpenseaMap[tokenId-1]);

            require(count > 0, "genesis : sender is not owner");

            IERC1155(oldGenesis).safeTransferFrom(msg.sender, nftOwner, tokenToOpenseaMap[tokenId-1], 1, "");

            _safeMint(msg.sender,tokenId);
            // super._safeTransfer(nftOwner, msg.sender, tokenId, "");
        }

        emit Claim(_tokenIds);
    }

    /**
     * @dev Get `baseTokenURI`
     * Overrided
     */
    function _baseURI() internal view virtual override returns (string memory) {
        return baseTokenURI;
    }

    /**
     * @dev Set `baseTokenURI`
     */
    function setBaseURI(string memory baseURI) public onlyOwner {
        require(bytes(baseURI).length > 0, "genesis : base URI invalid");
        baseTokenURI = baseURI;

        emit SetBaseTokenURI(baseURI);
    }

    function editOpenseaToken(uint index,uint token) external onlyOwner{
        tokenToOpenseaMap[index] = token;
    }

    function setOldGenesis(address _oldGenesis) public onlyOwner {
        oldGenesis = _oldGenesis;
    }
}
// import "./interfaces/IERC1155Interface.sol";
function _baseURI() internal view virtual override returns (string memory) {
    return baseTokenURI;
}

/**
 * @dev Get `baseTokenURI`
 * Overrided
 */