mirror of
https://github.com/bitsocialnet/5chan.git
synced 2026-08-03 07:41:04 +02:00
captcha modal design
This commit is contained in:
@@ -20,6 +20,7 @@
|
|||||||
"postcss": "^8.4.21",
|
"postcss": "^8.4.21",
|
||||||
"react": "^18.2.0",
|
"react": "^18.2.0",
|
||||||
"react-dom": "^18.2.0",
|
"react-dom": "^18.2.0",
|
||||||
|
"react-draggable": "^4.4.5",
|
||||||
"react-helmet-async": "^1.3.0",
|
"react-helmet-async": "^1.3.0",
|
||||||
"react-infinite-scroller": "^1.2.6",
|
"react-infinite-scroller": "^1.2.6",
|
||||||
"react-is": "^18.2.0",
|
"react-is": "^18.2.0",
|
||||||
|
|||||||
+250
-64
@@ -2,87 +2,253 @@ import React from 'react';
|
|||||||
import useBoardStore from '../useBoardStore';
|
import useBoardStore from '../useBoardStore';
|
||||||
import Modal from 'react-modal';
|
import Modal from 'react-modal';
|
||||||
import styled from 'styled-components';
|
import styled from 'styled-components';
|
||||||
|
import Draggable from 'react-draggable';
|
||||||
|
|
||||||
|
|
||||||
const StyledModal = styled(Modal)`
|
const StyledModal = styled(Modal)`
|
||||||
|
.hide-modal-overlay {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
|
||||||
.modal-content {
|
.modal-content {
|
||||||
width: 400px;
|
position: fixed;
|
||||||
height: 300px;
|
|
||||||
display: flex;
|
|
||||||
align-self: center;
|
|
||||||
flex-direction: column;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
position: absolute;
|
|
||||||
top: 50%;
|
top: 50%;
|
||||||
left: 50%;
|
left: 50%;
|
||||||
transform: translate(-50%, -50%);
|
transform: translate(-50%, -50%);
|
||||||
background-color: rgba(0, 0, 0, 0.75);
|
display: block;
|
||||||
padding: 0;
|
padding: 2px;
|
||||||
z-index: 9999;
|
font-size: 10pt;
|
||||||
border: 1px solid #aaa;
|
border-left: none;
|
||||||
|
border-top: none;
|
||||||
}
|
}
|
||||||
|
|
||||||
button.x {
|
.modal-header {
|
||||||
position: absolute;
|
font-size: 10pt;
|
||||||
top: 10px;
|
text-align: center;
|
||||||
right: 10px;
|
margin-bottom: 1px;
|
||||||
|
padding: 0;
|
||||||
|
height: 18px;
|
||||||
|
line-height: 18px;
|
||||||
|
cursor: move;
|
||||||
|
font-weight: 700;
|
||||||
|
}
|
||||||
|
|
||||||
|
.icon {
|
||||||
|
all: unset;
|
||||||
|
float: right;
|
||||||
|
cursor: pointer;
|
||||||
|
margin-bottom: -4px;
|
||||||
|
width: 18px;
|
||||||
|
height: 18px;
|
||||||
|
border: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
#name {
|
||||||
|
border: 1px solid #aaa;
|
||||||
|
font-family: Arial, Helvetica, sans-serif;
|
||||||
|
font-size: 10pt;
|
||||||
|
outline: medium none;
|
||||||
|
width: 298px;
|
||||||
|
padding: 2px;
|
||||||
|
}
|
||||||
|
|
||||||
|
textarea {
|
||||||
|
min-width: 296px;
|
||||||
|
float: left;
|
||||||
|
font-size: 10pt;
|
||||||
|
font-family: Arial, Helvetica, sans-serif;
|
||||||
|
}
|
||||||
|
|
||||||
|
#captcha-container {
|
||||||
|
position: relative;
|
||||||
|
clear: both;
|
||||||
|
width: 302px;
|
||||||
|
overflow: hidden;
|
||||||
|
margin-bottom: 3px;
|
||||||
|
}
|
||||||
|
|
||||||
|
#response {
|
||||||
|
width: 100%;
|
||||||
|
box-sizing: border-box;
|
||||||
|
font-size: 11px;
|
||||||
|
height: 18px;
|
||||||
|
margin: 0px;
|
||||||
|
padding: 0px 2px;
|
||||||
|
font-family: monospace;
|
||||||
|
vertical-align: middle;
|
||||||
}
|
}
|
||||||
|
|
||||||
img {
|
img {
|
||||||
width: 300px;
|
height: 100%;
|
||||||
height: 100px;
|
width: 100%;
|
||||||
object-fit: contain;
|
margin-top: 2px;
|
||||||
|
position: relative;
|
||||||
|
display: block;
|
||||||
}
|
}
|
||||||
|
|
||||||
.challenge {
|
#next {
|
||||||
font-size: 12pt;
|
float: right;
|
||||||
margin-bottom: 40px;
|
margin: 0;
|
||||||
font-weight: 700;
|
width: 75px;
|
||||||
color: #fff;
|
|
||||||
}
|
|
||||||
|
|
||||||
input {
|
|
||||||
margin-top: 30px;
|
|
||||||
width: 300px;
|
|
||||||
padding: 2px;
|
|
||||||
border: 1px solid #ccc;
|
|
||||||
font-family: monospace;
|
|
||||||
border: 1px solid #777;
|
|
||||||
outline: none;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
${({ selectedStyle }) => {
|
${({ selectedStyle }) => {
|
||||||
switch (selectedStyle) {
|
switch (selectedStyle) {
|
||||||
case 'Yotsuba':
|
case 'Yotsuba':
|
||||||
return ``;
|
return `
|
||||||
|
.modal-content {
|
||||||
|
background-color: #f0e0d6;
|
||||||
|
border: 1px solid #d9bfb7;
|
||||||
|
}
|
||||||
|
|
||||||
case 'Yotsuba B':
|
.modal-header {
|
||||||
return ``;
|
background-color: #ea8;
|
||||||
|
color: #800;
|
||||||
|
border: 1px solid #800;
|
||||||
|
}
|
||||||
|
|
||||||
|
.icon {
|
||||||
|
background-image: url(/assets/buttons/cross_red.png);
|
||||||
|
}
|
||||||
|
|
||||||
|
span {
|
||||||
|
color: maroon;
|
||||||
|
}`;
|
||||||
|
|
||||||
|
case 'Yotsuba-B':
|
||||||
|
return `
|
||||||
|
.modal-content {
|
||||||
|
background-color: #d6daf0;
|
||||||
|
border: 1px solid #b7c5d9;
|
||||||
|
}
|
||||||
|
|
||||||
|
.modal-header {
|
||||||
|
background-color: #98e;
|
||||||
|
color: #000;
|
||||||
|
border: 1px solid #000;
|
||||||
|
}
|
||||||
|
|
||||||
|
.icon {
|
||||||
|
background-image: url(/assets/buttons/cross_blue.png);
|
||||||
|
}
|
||||||
|
|
||||||
|
span {
|
||||||
|
color: #000;
|
||||||
|
}`;
|
||||||
|
|
||||||
case 'Futaba':
|
case 'Futaba':
|
||||||
return ``;
|
return `
|
||||||
|
.modal-content {
|
||||||
|
background-color: #f0e0d6;
|
||||||
|
border: 1px solid #d9bfb7;
|
||||||
|
}
|
||||||
|
|
||||||
|
.modal-header {
|
||||||
|
background-color: #ea8;
|
||||||
|
color: #800;
|
||||||
|
border: 1px solid #800;
|
||||||
|
}
|
||||||
|
|
||||||
|
.icon {
|
||||||
|
background-image: url(/assets/buttons/cross_red.png);
|
||||||
|
}
|
||||||
|
|
||||||
|
span {
|
||||||
|
color: maroon;
|
||||||
|
}`;
|
||||||
|
|
||||||
case 'Burichan':
|
case 'Burichan':
|
||||||
return ``;
|
return `
|
||||||
|
.modal-content {
|
||||||
|
background-color: #d6daf0;
|
||||||
|
border: 1px solid #b7c5d9;
|
||||||
|
}
|
||||||
|
|
||||||
|
.modal-header {
|
||||||
|
background-color: #98e;
|
||||||
|
color: #000;
|
||||||
|
border: 1px solid #000;
|
||||||
|
}
|
||||||
|
|
||||||
|
.icon {
|
||||||
|
background-image: url(/assets/buttons/cross_blue.png);
|
||||||
|
}
|
||||||
|
|
||||||
|
span {
|
||||||
|
color: #000;
|
||||||
|
}`;
|
||||||
|
|
||||||
case 'Tomorrow':
|
case 'Tomorrow':
|
||||||
return ``;
|
return `
|
||||||
|
.modal-content {
|
||||||
|
background-color: #282a2e;
|
||||||
|
border: 1px solid #111;
|
||||||
|
}
|
||||||
|
|
||||||
|
.modal-header {
|
||||||
|
background-color: #282a2e;
|
||||||
|
color: #c5c8c6;
|
||||||
|
}
|
||||||
|
|
||||||
|
.icon {
|
||||||
|
background-image: url(/assets/buttons/cross_dark.png);
|
||||||
|
}
|
||||||
|
|
||||||
|
#name {
|
||||||
|
background-color: #282a2e;
|
||||||
|
color: #c5c8c6;
|
||||||
|
border: 1px solid #515151;
|
||||||
|
width: 296px;
|
||||||
|
}
|
||||||
|
|
||||||
|
textarea {
|
||||||
|
background-color: #282a2e;
|
||||||
|
color: #c5c8c6;
|
||||||
|
border: 1px solid #515151;
|
||||||
|
}
|
||||||
|
|
||||||
|
#response {
|
||||||
|
background-color: #282a2e;
|
||||||
|
color: #c5c8c6;
|
||||||
|
outline: none;
|
||||||
|
border: 1px solid #515151;
|
||||||
|
}
|
||||||
|
|
||||||
|
span {
|
||||||
|
color: #c5c8c6;
|
||||||
|
}
|
||||||
|
|
||||||
|
#next {
|
||||||
|
filter: brightness(80%);
|
||||||
|
}`;
|
||||||
|
|
||||||
case 'Photon':
|
case 'Photon':
|
||||||
return ``;
|
return `
|
||||||
|
.modal-content {
|
||||||
|
background-color: #ddd;
|
||||||
|
border: 1px solid #ccc;
|
||||||
|
}
|
||||||
|
|
||||||
|
.modal-header {
|
||||||
|
background-color: #ddd;
|
||||||
|
color: #333;
|
||||||
|
}
|
||||||
|
|
||||||
|
.icon {
|
||||||
|
background-image: url(/assets/buttons/cross_photon.png);
|
||||||
|
}
|
||||||
|
|
||||||
|
span {
|
||||||
|
color: #333;
|
||||||
|
}`;
|
||||||
}
|
}
|
||||||
}}
|
}}
|
||||||
`;
|
`;
|
||||||
|
|
||||||
const customOverlayStyles = {
|
|
||||||
overlay: {
|
|
||||||
backgroundColor: 'rgba(0,0,0,.4)'
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
const CaptchaModal = ({ isOpen, closeModal, captchaImage }) => {
|
const CaptchaModal = ({ isOpen, closeModal, captchaImage }) => {
|
||||||
const { captchaResponse, setCaptchaResponse } = useBoardStore(state => state);
|
const { captchaResponse, setCaptchaResponse } = useBoardStore(state => state);
|
||||||
|
const selectedStyle = useBoardStore(state => state.selectedStyle);
|
||||||
|
|
||||||
const handleCloseModal = () => {
|
const handleCloseModal = () => {
|
||||||
closeModal();
|
closeModal();
|
||||||
@@ -94,24 +260,44 @@ const CaptchaModal = ({ isOpen, closeModal, captchaImage }) => {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<StyledModal
|
<StyledModal
|
||||||
isOpen={isOpen}
|
isOpen={isOpen}
|
||||||
onRequestClose={closeModal}
|
onRequestClose={closeModal}
|
||||||
shouldCloseOnOverlayClick={false}
|
contentLabel="Captcha Modal"
|
||||||
contentLabel="Captcha Modal"
|
shouldCloseOnEsc={false}
|
||||||
style={customOverlayStyles}
|
shouldCloseOnOverlayClick={false}
|
||||||
>
|
selectedStyle={selectedStyle}
|
||||||
<div className="modal-content">
|
overlayClassName="hide-modal-overlay">
|
||||||
<button className='x' onClick={handleCloseModal}>X</button>
|
<Draggable handle=".modal-header">
|
||||||
<div className="challenge">Verification</div>
|
<div className="modal-content">
|
||||||
<img src={captchaImage} alt="captcha" />
|
<div className="modal-header">
|
||||||
<input
|
Challenges for
|
||||||
type="text"
|
<button className="icon" onClick={handleCloseModal} title="close" />
|
||||||
autoComplete='off'
|
</div>
|
||||||
placeholder="TYPE THE CAPTCHA HERE AND PRESS ENTER"
|
<div id="form">
|
||||||
value={captchaResponse}
|
<div>
|
||||||
onChange={handleChallengeResponse}
|
<input id="name" type="text" placeholder="Name" disabled></input>
|
||||||
autoFocus />
|
</div>
|
||||||
</div>
|
<div>
|
||||||
|
<textarea rows="4" placeholder="Comment" wrap="soft" disabled></textarea>
|
||||||
|
</div>
|
||||||
|
<div id="captcha-container">
|
||||||
|
<input
|
||||||
|
id="response"
|
||||||
|
type="text"
|
||||||
|
autoComplete='off'
|
||||||
|
placeholder="TYPE THE CAPTCHA HERE AND PRESS ENTER"
|
||||||
|
value={captchaResponse}
|
||||||
|
onChange={handleChallengeResponse}
|
||||||
|
autoFocus />
|
||||||
|
<img src={captchaImage} alt="captcha" />
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<span>Challenge 1 of 3</span>
|
||||||
|
<button id="next">Next</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</Draggable>
|
||||||
</StyledModal>
|
</StyledModal>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -472,12 +472,6 @@ const Thread = ({ setBodyStyle }) => {
|
|||||||
<td id="td-name">Name</td>
|
<td id="td-name">Name</td>
|
||||||
<td>
|
<td>
|
||||||
<input name="name" type="text" tabIndex={1} placeholder="Anonymous" value={name} onChange={(event) => setName(event.target.value)} />
|
<input name="name" type="text" tabIndex={1} placeholder="Anonymous" value={name} onChange={(event) => setName(event.target.value)} />
|
||||||
</td>
|
|
||||||
</tr>
|
|
||||||
<tr data-type="Subject">
|
|
||||||
<td>Subject</td>
|
|
||||||
<td>
|
|
||||||
<input name="sub" type="text" tabIndex={3} value={subject} onChange={(event) => setSubject(event.target.value)} />
|
|
||||||
<input id="post-button" type="submit" value="Post" tabIndex={6} onClick={handlePublishComment} />
|
<input id="post-button" type="submit" value="Post" tabIndex={6} onClick={handlePublishComment} />
|
||||||
</td>
|
</td>
|
||||||
</tr>
|
</tr>
|
||||||
|
|||||||
@@ -10024,6 +10024,14 @@ react-dom@^18.2.0:
|
|||||||
loose-envify "^1.1.0"
|
loose-envify "^1.1.0"
|
||||||
scheduler "^0.23.0"
|
scheduler "^0.23.0"
|
||||||
|
|
||||||
|
react-draggable@^4.4.5:
|
||||||
|
version "4.4.5"
|
||||||
|
resolved "https://registry.yarnpkg.com/react-draggable/-/react-draggable-4.4.5.tgz#9e37fe7ce1a4cf843030f521a0a4cc41886d7e7c"
|
||||||
|
integrity sha512-OMHzJdyJbYTZo4uQE393fHcqqPYsEtkjfMgvCHr6rejT+Ezn4OZbNyGH50vv+SunC1RMvwOTSWkEODQLzw1M9g==
|
||||||
|
dependencies:
|
||||||
|
clsx "^1.1.1"
|
||||||
|
prop-types "^15.8.1"
|
||||||
|
|
||||||
react-error-overlay@^6.0.11:
|
react-error-overlay@^6.0.11:
|
||||||
version "6.0.11"
|
version "6.0.11"
|
||||||
resolved "https://registry.yarnpkg.com/react-error-overlay/-/react-error-overlay-6.0.11.tgz#92835de5841c5cf08ba00ddd2d677b6d17ff9adb"
|
resolved "https://registry.yarnpkg.com/react-error-overlay/-/react-error-overlay-6.0.11.tgz#92835de5841c5cf08ba00ddd2d677b6d17ff9adb"
|
||||||
|
|||||||
Reference in New Issue
Block a user