/** * This file is part of the SplendidBear Websites' projects. * * Copyright (c) 2026 @ www.splendidbear.org * * For the full copyright and license information, please view the LICENSE * file that was distributed with this source code. */ import React, { Fragment, useCallback, useEffect, useMemo, useState } from 'react'; import { func, node, string } from 'prop-types'; const CAPTCHA_STORAGE_KEY = 'mineseeker_captcha_verified'; const CAPTCHA_TOKEN_KEY = 'mineseeker_captcha_token'; const RECAPTCHA_ACTION = 'mineseeker_play'; const CaptchaOverlay = ({ siteKey, onVerified, children }) => { const [verified, setVerified] = useState(false); const [loading, setLoading] = useState(false); const [error, setError] = useState(false); const handleToken = useCallback(token => { const wrapper = document.getElementById('mine-wrapper'); if (wrapper) { wrapper.dataset.captchaToken = token; } sessionStorage.setItem(CAPTCHA_TOKEN_KEY, token); sessionStorage.setItem(CAPTCHA_STORAGE_KEY, Date.now().toString()); setVerified(true); onVerified?.(); }, [onVerified]); const buttonClasses = useMemo(() => [ 'captcha-button', error && 'captcha-button--error', loading && 'captcha-button--loading', ].filter(Boolean).join(' '), [error, loading]); useEffect(() => { const storedToken = sessionStorage.getItem(CAPTCHA_TOKEN_KEY); const storedTime = sessionStorage.getItem(CAPTCHA_STORAGE_KEY); if (storedToken && storedTime) { const elapsed = (Date.now() - parseInt(storedTime)) / 1000; if (110 > elapsed) { const wrapper = document.getElementById('mine-wrapper'); if (wrapper) { wrapper.dataset.captchaToken = storedToken; } setVerified(true); onVerified?.(); return; } } if (window.grecaptcha) { window.grecaptcha.ready(() => { window.grecaptcha .execute(siteKey, { action: RECAPTCHA_ACTION }) .then(token => { handleToken(token); }) .catch(() => { setError(true); }); }); } }, [siteKey, onVerified, handleToken]); const handleClick = () => { setLoading(true); setError(false); window.grecaptcha.ready(() => { window.grecaptcha .execute(siteKey, { action: RECAPTCHA_ACTION }) .then(token => { handleToken(token); setLoading(false); }) .catch(() => { setLoading(false); setError(true); setTimeout(() => setError(false), 2000); }); }); }; if (verified) { return {children}; } return (

Ready to Play?

Click below to verify you're human and start playing.

); }; export default CaptchaOverlay; CaptchaOverlay.propTypes = { siteKey: string.isRequired, onVerified: func, children: node, };