Magnet input: keydown

This commit is contained in:
Igor Katson 2023-12-14 12:42:22 +00:00
parent 5a30b3fb0c
commit 74ae3cfca2
No known key found for this signature in database
GPG key ID: B4EC22B66D61A3F5
9 changed files with 59 additions and 49 deletions

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View file

@ -4,14 +4,14 @@
"src": "assets/logo.svg" "src": "assets/logo.svg"
}, },
"index.css": { "index.css": {
"file": "assets/index-bc066ae5.css", "file": "assets/index-458d2033.css",
"src": "index.css" "src": "index.css"
}, },
"index.html": { "index.html": {
"css": [ "css": [
"assets/index-bc066ae5.css" "assets/index-458d2033.css"
], ],
"file": "assets/index-9469b905.js", "file": "assets/index-1daa8daf.js",
"isEntry": true, "isEntry": true,
"src": "index.html" "src": "index.html"
} }

View file

@ -1,19 +1,18 @@
import { ReactNode } from "react"; import { ReactNode } from "react";
export const Button: React.FC<{ export const Button: React.FC<{
onClick: React.MouseEventHandler<HTMLButtonElement>; onClick: () => void;
variant?: "cancel" | "primary" | "secondary" | "danger" | "none"; variant?: "cancel" | "primary" | "secondary" | "danger" | "none";
className?: string; className?: string;
disabled?: boolean; disabled?: boolean;
children: ReactNode; children: ReactNode;
}> = ({ onClick, children, className, disabled, variant }) => { }> = ({ onClick, children, className, disabled, variant }) => {
let variantClassNames = { let variantClassNames = {
secondary: secondary: "hover:bg-blue-500 transition-colors hover:text-white",
"hover:bg-blue-600 transition-colors duration-100 hover:text-white",
danger: danger:
"bg-red-500 text-white border-green-50 hover:border-red-700 hover:bg-red-600", "bg-red-400 text-white border-green-50 hover:border-red-700 hover:bg-red-600",
primary: "bg-blue-400 text-white hover:bg-blue-600", primary: "bg-blue-600 text-white hover:bg-blue-800 disabled:bg-blue-200",
cancel: "bg-slate-50 hover:bg-slate-200", cancel: "hover:bg-slate-200",
none: "", none: "",
}[variant ?? "secondary"]; }[variant ?? "secondary"];
return ( return (
@ -21,7 +20,7 @@ export const Button: React.FC<{
disabled={disabled} disabled={disabled}
onClick={(e) => { onClick={(e) => {
e.preventDefault(); e.preventDefault();
onClick(e); onClick();
}} }}
className={`flex inline-flex items-center gap-1 border rounded-lg border disabled:cursor-not-allowed px-2 py-1 transition-colors duration-300 ${variantClassNames} ${className}`} className={`flex inline-flex items-center gap-1 border rounded-lg border disabled:cursor-not-allowed px-2 py-1 transition-colors duration-300 ${variantClassNames} ${className}`}
> >

View file

@ -12,6 +12,12 @@ export const MagnetInput = ({ className }: { className?: string }) => {
const [inputValue, setInputValue] = useState(""); const [inputValue, setInputValue] = useState("");
const [modalIsOpen, setModalIsOpen] = useState(false); const [modalIsOpen, setModalIsOpen] = useState(false);
const submit = () => {
setMagnet(inputValue);
setInputValue("");
setModalIsOpen(false);
};
const clear = () => { const clear = () => {
setModalIsOpen(false); setModalIsOpen(false);
setMagnet(null); setMagnet(null);
@ -38,6 +44,11 @@ export const MagnetInput = ({ className }: { className?: string }) => {
value={inputValue} value={inputValue}
name="magnet" name="magnet"
onChange={(e) => setInputValue(e.target.value)} onChange={(e) => setInputValue(e.target.value)}
onKeyDown={(e) => {
if (e.key === "Enter" && !!inputValue) {
submit();
}
}}
placeholder="magnet:?xt=urn:btih:..." placeholder="magnet:?xt=urn:btih:..."
help="Enter magnet or HTTP(S) URL to the .torrent" help="Enter magnet or HTTP(S) URL to the .torrent"
/> />
@ -47,15 +58,7 @@ export const MagnetInput = ({ className }: { className?: string }) => {
<Button variant="cancel" onClick={clear}> <Button variant="cancel" onClick={clear}>
Cancel Cancel
</Button> </Button>
<Button <Button disabled={!inputValue} variant="primary" onClick={submit}>
disabled={!inputValue}
variant="primary"
onClick={() => {
setMagnet(inputValue);
setInputValue("");
setModalIsOpen(false);
}}
>
Add Add
</Button> </Button>
</ModalFooter> </ModalFooter>

View file

@ -7,13 +7,17 @@ export const Fieldset = ({
className, className,
}: { }: {
children: ReactNode; children: ReactNode;
label: string; label?: string;
help?: string; help?: string;
className?: string; className?: string;
}) => { }) => {
return ( return (
<fieldset className={`mb-4 ${className}`}> <fieldset className={`mb-4 ${className}`}>
<label className="text-md font-md mb-3 block">{label}</label> {label && (
<label className="text-md font-md mb-3 block pb-1 border-b">
{label}
</label>
)}
{children} {children}
</fieldset> </fieldset>
); );

View file

@ -6,6 +6,7 @@ export const FormInput: React.FC<{
autoFocus?: boolean; autoFocus?: boolean;
name: string; name: string;
inputType?: string; inputType?: string;
onKeyDown?: React.KeyboardEventHandler<HTMLInputElement>;
placeholder?: string; placeholder?: string;
help?: string; help?: string;
disabled?: boolean; disabled?: boolean;
@ -16,13 +17,14 @@ export const FormInput: React.FC<{
name, name,
disabled, disabled,
onChange, onChange,
onKeyDown,
label, label,
help, help,
inputType, inputType,
placeholder, placeholder,
}) => { }) => {
return ( return (
<div className="flex flex-col gap-2 text-sm mb-6"> <div className="flex flex-col gap-2 text-sm mb-2">
<label htmlFor={name}>{label}</label> <label htmlFor={name}>{label}</label>
<input <input
autoFocus={autoFocus} autoFocus={autoFocus}
@ -33,9 +35,10 @@ export const FormInput: React.FC<{
disabled={disabled} disabled={disabled}
placeholder={placeholder} placeholder={placeholder}
value={value} value={value}
onKeyDown={onKeyDown}
onChange={onChange} onChange={onChange}
/> />
{help && <div className="text-xs text-slate-500 mb-3">{help}</div>} {help && <div className="text-xs text-slate-500">{help}</div>}
</div> </div>
); );
}; };

View file

@ -36,7 +36,6 @@ export const FileSelectionModal = (props: {
const [outputFolder, setOutputFolder] = useState<string>(""); const [outputFolder, setOutputFolder] = useState<string>("");
const ctx = useContext(AppContext); const ctx = useContext(AppContext);
const API = useContext(APIContext); const API = useContext(APIContext);
// const [Modal, , , closeModal] = useModal({ fullScreen: true });
const selectAll = () => { const selectAll = () => {
setSelectedFiles( setSelectedFiles(
@ -108,7 +107,16 @@ export const FileSelectionModal = (props: {
} else if (listTorrentResponse) { } else if (listTorrentResponse) {
return ( return (
<Form> <Form>
<Fieldset className="mb-4" label="Pick the files to download"> <FormInput
label="Output folder"
name="output_folder"
inputType="text"
value={outputFolder}
onChange={(e) => setOutputFolder(e.target.value)}
/>
<Fieldset>
<label className="text-sm mb-2 block">Select files</label>
<div className="mb-3 flex gap-2"> <div className="mb-3 flex gap-2">
<Button onClick={selectAll} className="text-sm"> <Button onClick={selectAll} className="text-sm">
Select all Select all
@ -127,15 +135,8 @@ export const FileSelectionModal = (props: {
/> />
))} ))}
</Fieldset> </Fieldset>
<Fieldset label="Options">
<FormInput
label="Output folder"
name="output_folder"
inputType="text"
value={outputFolder}
onChange={(e) => setOutputFolder(e.target.value)}
/>
{/* <Fieldset label="Options">
<FormCheckbox <FormCheckbox
label="Increase timeouts" label="Increase timeouts"
checked={unpopularTorrent} checked={unpopularTorrent}
@ -143,7 +144,7 @@ export const FileSelectionModal = (props: {
help="This might be useful for unpopular torrents with few peers. It will slow down fast torrents though." help="This might be useful for unpopular torrents with few peers. It will slow down fast torrents though."
name="increase_timeouts" name="increase_timeouts"
/> />
</Fieldset> </Fieldset> */}
</Form> </Form>
); );
} }

View file

@ -210,7 +210,7 @@ export const ConfigModal: React.FC<{
</Tab> </Tab>
<Tab name="DHT" currentTab={tab}> <Tab name="DHT" currentTab={tab}>
<Fieldset label="DHT config"> <Fieldset>
<FormCheck <FormCheck
label="Enable DHT" label="Enable DHT"
name="dht.disable" name="dht.disable"
@ -241,7 +241,7 @@ export const ConfigModal: React.FC<{
</Tab> </Tab>
<Tab name="TCP Listen" currentTab={tab}> <Tab name="TCP Listen" currentTab={tab}>
<Fieldset label="TCP Listener config"> <Fieldset>
<FormCheck <FormCheck
label="Listen on TCP" label="Listen on TCP"
name="tcp_listen.disable" name="tcp_listen.disable"
@ -281,7 +281,7 @@ export const ConfigModal: React.FC<{
</Tab> </Tab>
<Tab name="Session" currentTab={tab}> <Tab name="Session" currentTab={tab}>
<Fieldset label="Session persistence"> <Fieldset>
<FormCheck <FormCheck
label="Enable persistence" label="Enable persistence"
name="persistence.disable" name="persistence.disable"
@ -302,7 +302,7 @@ export const ConfigModal: React.FC<{
</Tab> </Tab>
<Tab name="Peer options" currentTab={tab}> <Tab name="Peer options" currentTab={tab}>
<Fieldset label="Peer connection options"> <Fieldset>
<FormInput <FormInput
label="Connect timeout (seconds)" label="Connect timeout (seconds)"
inputType="number" inputType="number"
@ -324,7 +324,7 @@ export const ConfigModal: React.FC<{
</Tab> </Tab>
<Tab name="HTTP API" currentTab={tab}> <Tab name="HTTP API" currentTab={tab}>
<Fieldset label="HTTP API config"> <Fieldset>
<FormCheck <FormCheck
label="Enable HTTP API" label="Enable HTTP API"
name="http_api.disable" name="http_api.disable"
@ -365,7 +365,7 @@ export const ConfigModal: React.FC<{
</ModalBody> </ModalBody>
<ModalFooter> <ModalFooter>
{!!handleCancel && ( {!!handleCancel && (
<Button variant="secondary" onClick={handleCancel}> <Button variant="cancel" onClick={handleCancel}>
Cancel Cancel
</Button> </Button>
)} )}