feat: add text uplading

This commit is contained in:
dicedtomato 2022-07-09 23:54:55 +00:00 committed by GitHub
parent 964199f8a9
commit 2f90193d7e
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
5 changed files with 174 additions and 35 deletions

View file

@ -0,0 +1,21 @@
import { createStyles, MantineSize, Textarea } from '@mantine/core';
const useStyles = createStyles((theme, { size }: { size: MantineSize }) => ({
input: {
fontFamily: 'monospace',
fontSize: theme.fn.size({ size, sizes: theme.fontSizes }) - 2,
height: '100vh',
},
}));
export default function CodeInput({ ...props }) {
const { classes } = useStyles({ size: 'md' }, { name: 'CodeInput' });
return (
<Textarea
classNames={{ input: classes.input }}
autoComplete='nope'
{...props}
/>
);
}

View file

@ -2,7 +2,7 @@ import { AppShell, Box, Burger, Divider, Group, Header, MediaQuery, Navbar, Pape
import { useClipboard } from '@mantine/hooks';
import { useModals } from '@mantine/modals';
import { useNotifications } from '@mantine/notifications';
import { CheckIcon, CopyIcon, Cross1Icon, FileIcon, GearIcon, HomeIcon, Link1Icon, MixerHorizontalIcon, Pencil1Icon, PersonIcon, PinRightIcon, ResetIcon, UploadIcon } from '@modulz/radix-icons';
import { CheckIcon, CopyIcon, Cross1Icon, FileIcon, GearIcon, HomeIcon, Link1Icon, MixerHorizontalIcon, Pencil1Icon, PersonIcon, PinRightIcon, ResetIcon, TextIcon, UploadIcon } from '@modulz/radix-icons';
import useFetch from 'hooks/useFetch';
import { updateUser } from 'lib/redux/reducers/user';
import { useStoreDispatch } from 'lib/redux/store';
@ -88,6 +88,11 @@ const items = [
text: 'Upload',
link: '/dashboard/upload',
},
{
icon: <TextIcon />,
text: 'Upload Text',
link: '/dashboard/text',
},
];
export default function Layout({ children, user }) {

View file

@ -0,0 +1,87 @@
import { Button, Collapse, Group, Progress, Select, Title, useMantineTheme } from '@mantine/core';
import { randomId, useClipboard } from '@mantine/hooks';
import { useNotifications } from '@mantine/notifications';
import { CrossCircledIcon, LetterCaseCapitalizeIcon, LetterCaseLowercaseIcon, UploadIcon } from '@modulz/radix-icons';
import CodeInput from 'components/CodeInput';
import Dropzone from 'components/dropzone/Dropzone';
import FileDropzone from 'components/dropzone/DropzoneFile';
import Link from 'components/Link';
import exts from 'lib/exts';
import { useStoreSelector } from 'lib/redux/store';
import { useEffect, useState } from 'react';
export default function Upload() {
const notif = useNotifications();
const clipboard = useClipboard();
const user = useStoreSelector(state => state.user);
const [progress, setProgress] = useState(0);
const [loading, setLoading] = useState(false);
const [value, setValue] = useState('');
const [lang, setLang] = useState('txt');
console.log(lang);
const handleUpload = async () => {
setProgress(0);
setLoading(true);
const file = new File([value], 'text.' + lang);
const id = notif.showNotification({
title: 'Uploading...',
message: '',
loading: true,
autoClose: false,
});
const req = new XMLHttpRequest();
req.upload.addEventListener('progress', e => {
if (e.lengthComputable) {
setProgress(Math.round(e.loaded / e.total * 100));
}
});
req.addEventListener('load', e => {
// @ts-ignore not sure why it thinks response doesnt exist, but it does.
const json = JSON.parse(e.target.response);
setLoading(false);
if (!json.error) {
notif.updateNotification(id, {
title: 'Upload Successful',
message: <>Copied first file to clipboard! <br />{json.files.map(x => (<Link key={x} href={x}>{x}<br /></Link>))}</>,
});
}
});
const body = new FormData();
body.append('file', file);
req.open('POST', '/api/upload');
req.setRequestHeader('Authorization', user.token);
req.send(body);
};
return (
<>
<Title mb='md'>Upload Text</Title>
<CodeInput
value={value}
onChange={e => setValue(e.target.value)}
/>
<Group position='right' mt='md'>
<Select
value={lang}
onChange={setLang}
dropdownPosition='top'
data={Object.keys(exts).map(x => ({ value: x, label: exts[x] }))}
icon={<LetterCaseCapitalizeIcon />}
/>
<Button leftIcon={<UploadIcon />} onClick={handleUpload}>Upload</Button>
</Group>
</>
);
}

View file

@ -1,40 +1,45 @@
// https://github.com/toptal/haste-server/blob/master/static/application.js#L167-L174
// Popular extension map
const exts = {
rb: 'ruby',
py: 'python',
pl: 'perl',
php: 'php',
scala: 'scala',
go: 'go',
xml: 'xml',
html: 'xml',
htm: 'xml',
css: 'css',
js: 'javascript',
json: 'json',
vbs: 'vbscript',
lua: 'lua',
pas: 'delphi',
java: 'java',
cpp: 'cpp',
cc: 'cpp',
m: 'objectivec',
vala: 'vala',
sql: 'sql',
sm: 'smalltalk',
lisp: 'lisp',
ini: 'ini',
diff: 'diff',
bash: 'bash',
sh: 'bash',
tex: 'tex',
erl: 'erlang',
hs: 'haskell',
md: 'markdown',
txt: '',
coffee: 'coffee',
swift: 'swift',
'md': 'Markdown',
'css': 'CSS',
'js': 'JavaScript',
'json': 'JSON',
'html': 'HTML',
'ts': 'TypeScript',
'java': 'Java',
'py': 'Python',
'rb': 'Ruby',
'sh': 'Shell',
'php': 'PHP',
'pl': 'Perl',
'sql': 'SQL',
'xml': 'XML',
'yml': 'YAML',
'yaml': 'YAML',
'c': 'C',
'cpp': 'C++',
'cs': 'C#',
'go': 'Go',
'h': 'C/C++ Header',
'txt': 'Text',
'dockerfile': 'Dockerfile',
'toml': 'TOML',
'ini': 'INI',
'bat': 'Batch File',
'tex': 'TeX',
'r': 'R',
'lua': 'Lua',
'ps1': 'PowerShell',
'rst': 'reStructuredText',
'rs': 'Rust',
'swift': 'Swift',
'scss': 'SCSS',
'less': 'LESS',
'scala': 'Scala',
'kotlin': 'Kotlin',
'vb': 'Visual Basic',
'vim': 'Vim Script',
};
export default exts;

View file

@ -0,0 +1,21 @@
import React from 'react';
import useLogin from 'hooks/useLogin';
import Layout from 'components/Layout';
import UploadText from 'components/pages/UploadText';
import { LoadingOverlay } from '@mantine/core';
export default function UploadTextPage() {
const { user, loading } = useLogin();
if (loading) return <LoadingOverlay visible={loading} />;
return (
<Layout
user={user}
>
<UploadText/>
</Layout>
);
}
UploadTextPage.title = 'Zipline - Upload Text';