Ported from old SvelteKit version
This commit is contained in:
commit
61e65915ca
16 changed files with 3566 additions and 0 deletions
11
.gitignore
vendored
Normal file
11
.gitignore
vendored
Normal file
|
@ -0,0 +1,11 @@
|
|||
.DS_Store
|
||||
node_modules
|
||||
/build
|
||||
/.svelte-kit
|
||||
/package
|
||||
.env
|
||||
.env.*
|
||||
!.env.example
|
||||
vite.config.js.timestamp-*
|
||||
vite.config.ts.timestamp-*
|
||||
db
|
2708
package-lock.json
generated
Normal file
2708
package-lock.json
generated
Normal file
File diff suppressed because it is too large
Load diff
27
package.json
Normal file
27
package.json
Normal file
|
@ -0,0 +1,27 @@
|
|||
{
|
||||
"name": "my-app",
|
||||
"version": "0.0.1",
|
||||
"private": true,
|
||||
"scripts": {
|
||||
"dev": "vite dev",
|
||||
"build": "vite build",
|
||||
"preview": "vite preview"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@sveltejs/adapter-auto": "^1.0.0",
|
||||
"@sveltejs/kit": "^1.0.0",
|
||||
"svelte": "^3.54.0",
|
||||
"vite": "^4.0.0"
|
||||
},
|
||||
"type": "module",
|
||||
"dependencies": {
|
||||
"@sveltejs/adapter-cloudflare": "^2.1.0",
|
||||
"@sveltejs/adapter-node": "^1.1.1",
|
||||
"archiver": "^5.3.1",
|
||||
"crypto": "^1.0.1",
|
||||
"dotenv": "^16.0.3",
|
||||
"image-size": "^1.0.2",
|
||||
"sqlite": "^4.1.2",
|
||||
"sqlite3": "^5.1.4"
|
||||
}
|
||||
}
|
20
src/app.html
Normal file
20
src/app.html
Normal file
|
@ -0,0 +1,20 @@
|
|||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<link rel="icon" href="%sveltekit.assets%/favicon.png" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
||||
%sveltekit.head%
|
||||
<style>
|
||||
body {
|
||||
font-family: monospace;
|
||||
padding: 0;
|
||||
margin: 0;
|
||||
overflow-x: hidden;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<div>%sveltekit.body%</div>
|
||||
</body>
|
||||
</html>
|
146
src/lib/Main.svelte
Normal file
146
src/lib/Main.svelte
Normal file
|
@ -0,0 +1,146 @@
|
|||
<script>
|
||||
export let textTop = "";
|
||||
export let textBottom = "";
|
||||
export let fgColor = "var(--grayish)"; //"rgb(255,255,255)";
|
||||
export let bgColor = "var(--grayish)"; //"rgb(255,255,255)";
|
||||
export let bgImg = "url('/img/bg.svg')";
|
||||
export let download = "/";
|
||||
export let date = "N/A";
|
||||
export let turbowarp = false;
|
||||
export let classes = "";
|
||||
|
||||
var changeTheme = function () {
|
||||
localStorage.setItem(
|
||||
"theme",
|
||||
localStorage.getItem("theme") == "dark" ? "" : "dark"
|
||||
);
|
||||
window.location.href = "";
|
||||
};
|
||||
</script>
|
||||
|
||||
<body style="--bg-bg: {bgColor}; --bg-fg: {fgColor}" class={classes}>
|
||||
<div class="banner-wrapper">
|
||||
<div class="banner" style="background-image: {bgImg}">
|
||||
<div class="banner-text">
|
||||
<p>
|
||||
{textTop}
|
||||
<a
|
||||
class="download"
|
||||
download={textTop.split("/").pop()}
|
||||
href={download}>(Download)</a
|
||||
> <a href="././" class="download">(../)</a>
|
||||
<a href="/" class="download">(/)</a>
|
||||
{#if turbowarp}
|
||||
<a
|
||||
class="download"
|
||||
href="https://turbowarp.org/editor?project_url={download}"
|
||||
>(TurboWarp)</a
|
||||
>
|
||||
{/if}
|
||||
</p>
|
||||
</div>
|
||||
<slot />
|
||||
<div class="banner-text">
|
||||
{textBottom}
|
||||
<a href="https://tdgmdev.net/" class="download">(Home)</a>
|
||||
<a href="#" class="download" on:click={changeTheme}
|
||||
>(Change theme)</a
|
||||
>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</body>
|
||||
|
||||
<style lang="css">
|
||||
body {
|
||||
--blue: #4689e8;
|
||||
--blue-again: #5687d9;
|
||||
--white: rgb(255, 255, 255);
|
||||
--grayish: rgb(240, 240, 240);
|
||||
--gray: rgb(210, 210, 210);
|
||||
--black: rgb(0, 0, 0);
|
||||
|
||||
color: var(--black);
|
||||
}
|
||||
.dark {
|
||||
--white: rgb(32, 32, 32);
|
||||
--grayish: rgb(47, 47, 47);
|
||||
--gray: rgb(70, 70, 70);
|
||||
--black: rgb(255, 255, 255);
|
||||
--blue: rgb(128, 128, 128);
|
||||
--blue-again: rgb(190, 190, 190);
|
||||
}
|
||||
|
||||
.banner {
|
||||
width: 100%;
|
||||
height: 100vh;
|
||||
background-size: auto 75%;
|
||||
background-position: center;
|
||||
background-repeat: no-repeat;
|
||||
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
font-weight: bold;
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
body {
|
||||
background: radial-gradient(
|
||||
circle at 5px 5px,
|
||||
var(--bg-fg) 1px,
|
||||
var(--bg-bg) 0px,
|
||||
var(--bg-bg) 8px
|
||||
);
|
||||
background-size: 10px 10px;
|
||||
background-repeat: repeat;
|
||||
/*background: url('/bg.png');
|
||||
background-size: cover;
|
||||
*/
|
||||
}
|
||||
|
||||
.banner-part {
|
||||
height: 500px;
|
||||
}
|
||||
|
||||
.banner-text {
|
||||
/*color: white;*/
|
||||
margin: 30px;
|
||||
/*filter: drop-shadow( 0px 0px 10px rgba(0, 0, 0, 1));*/
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.banner-mid {
|
||||
width: calc(100% - 50px);
|
||||
font-size: 12px;
|
||||
max-height: 100%;
|
||||
display: flex;
|
||||
justify-content: space-around;
|
||||
height: 100%;
|
||||
overflow: auto;
|
||||
font-weight: normal;
|
||||
}
|
||||
|
||||
.download {
|
||||
font-size: 50%;
|
||||
}
|
||||
|
||||
p {
|
||||
margin-block-start: 0;
|
||||
margin-block-end: 0;
|
||||
}
|
||||
|
||||
.banner-mid {
|
||||
border: solid var(--gray) 1px;
|
||||
border-radius: 10px;
|
||||
}
|
||||
|
||||
a {
|
||||
text-decoration: none;
|
||||
color: var(--blue-again);
|
||||
}
|
||||
|
||||
.dark {
|
||||
}
|
||||
</style>
|
8
src/routes/+page.svelte
Normal file
8
src/routes/+page.svelte
Normal file
|
@ -0,0 +1,8 @@
|
|||
<script context="module">
|
||||
export async function load() {
|
||||
return {
|
||||
status: 302,
|
||||
redirect: "/data/",
|
||||
};
|
||||
}
|
||||
</script>
|
69
src/routes/api/file/[...path]/+server.js
Normal file
69
src/routes/api/file/[...path]/+server.js
Normal file
|
@ -0,0 +1,69 @@
|
|||
import fs from 'fs';
|
||||
import archiver from 'archiver';
|
||||
import crypto from 'crypto';
|
||||
|
||||
|
||||
/** @type {import('./$types').RequestHandler} */
|
||||
export async function GET({ params }) {
|
||||
const DATA_DIRECTORY = "/files/";
|
||||
const ZIP_DIRECTORY = "/zips/";
|
||||
|
||||
let currDirectory = DATA_DIRECTORY + params.path;
|
||||
|
||||
currDirectory = currDirectory.replaceAll(/\/+/g,'/');
|
||||
|
||||
var path, contents;
|
||||
|
||||
if (currDirectory.indexOf('./') != -1 || currDirectory.indexOf('../') != -1 || currDirectory.indexOf('//') != -1 || !fs.existsSync(currDirectory)) {
|
||||
return new Response('Invalid Path');
|
||||
} else if (fs.lstatSync(currDirectory).isDirectory()) {
|
||||
|
||||
|
||||
var zipDir = ZIP_DIRECTORY + (crypto.createHash('md5').update(params.path).digest('hex')) + ".zip";
|
||||
|
||||
const files = fs.readdirSync(currDirectory);
|
||||
const stats = files.map(file => fs.statSync(currDirectory + '/' + file));
|
||||
|
||||
var recursive = false;
|
||||
files.forEach(file => {
|
||||
if (fs.statSync(currDirectory + '/' + file).isDirectory()) {
|
||||
recursive = true;
|
||||
return;
|
||||
}
|
||||
});
|
||||
|
||||
if (recursive == true) return new Response('Recursive directories cannot be downloaded.');
|
||||
|
||||
|
||||
const size = stats.reduce((accumulator, { size }) => accumulator + size, 0);
|
||||
if (size > 1024 * 1024 * 128) {
|
||||
return new Response('That directory is too large to request a download of.');
|
||||
}
|
||||
|
||||
const mtime = stats.reduce((accumulator, { mtime }) => Math.max(accumulator, mtime), 0);
|
||||
var updated = false;
|
||||
if (fs.existsSync(zipDir) && mtime > fs.statSync(zipDir).mtime) {
|
||||
fs.unlinkSync(zipDir);
|
||||
updated = true;
|
||||
}
|
||||
|
||||
if (!fs.existsSync(zipDir) || updated) {
|
||||
const output = fs.createWriteStream(zipDir);
|
||||
|
||||
const archive = archiver('zip', {
|
||||
zlib: { level: 9 }
|
||||
});
|
||||
|
||||
await new Promise((resolve, reject) => {
|
||||
archive.pipe(output);
|
||||
archive.directory(currDirectory, 'data');
|
||||
archive.finalize();
|
||||
output.on('close', resolve);
|
||||
});
|
||||
}
|
||||
|
||||
return new Response(fs.readFileSync(zipDir));
|
||||
} else {
|
||||
return new Response(fs.readFileSync(currDirectory));
|
||||
}
|
||||
}
|
104
src/routes/data/[...path]/+page.server.js
Normal file
104
src/routes/data/[...path]/+page.server.js
Normal file
|
@ -0,0 +1,104 @@
|
|||
import fs from 'fs';
|
||||
import sizeOf from 'image-size';
|
||||
|
||||
function compareFiles(a, b, dir) {
|
||||
|
||||
var oldA = a;
|
||||
var oldB = b;
|
||||
|
||||
a = dir + '/' + a;
|
||||
b = dir + '/' + b;
|
||||
|
||||
if (oldA[0] == '!' && oldB[0] != '!') return -1;
|
||||
if (oldB[0] == '!' && oldA[0] != '!') return;
|
||||
if (fs.statSync(a).isDirectory() && !fs.statSync(b).isDirectory()) return -1;
|
||||
if (fs.statSync(b).isDirectory() && !fs.statSync(a).isDirectory()) return 1;
|
||||
return (fs.statSync(b).mtime - fs.statSync(a).mtime);
|
||||
}
|
||||
|
||||
function getData(file, dir, path) {
|
||||
var fileData = fs.statSync(dir + '/' + file);
|
||||
|
||||
var suffix = "";
|
||||
if (fileData.isDirectory()) suffix += '/';
|
||||
|
||||
var d = fileData.mtime;
|
||||
|
||||
return {
|
||||
"name": file + suffix,
|
||||
"link": file,
|
||||
"dir": path + '/' + file,
|
||||
"mtime": d.toUTCString(),
|
||||
"extension": file.split('.').pop()
|
||||
};
|
||||
}
|
||||
|
||||
/** @type {import('./$types').PageLoad} */
|
||||
export async function load({ params, url }) {
|
||||
const DATA_DIRECTORY = "/files/";
|
||||
|
||||
let currDirectory = DATA_DIRECTORY + params.path;
|
||||
|
||||
var path, contents, raw, date;
|
||||
|
||||
var isDark = (url.searchParams.get('dark')) ? "dark" : "";
|
||||
|
||||
if (currDirectory.indexOf('./') != -1 || currDirectory.indexOf('../') != -1 || currDirectory.indexOf('//') != -1 || !fs.existsSync(currDirectory)) {
|
||||
path = "Invalid Path";
|
||||
contents = "";
|
||||
} else if (fs.statSync(currDirectory).isDirectory()) {
|
||||
var files = [];
|
||||
fs.readdirSync(currDirectory).forEach(file => {
|
||||
if (file.search(/dir\.zip$/) != -1) return;
|
||||
files.push(file);
|
||||
});
|
||||
files.sort(function (a, b) { return compareFiles(a, b, currDirectory) });
|
||||
if (params.path != '') {
|
||||
files = [".", "..", ...files];
|
||||
} else {
|
||||
files = [".", ...files];
|
||||
}
|
||||
|
||||
for (var i = 0; i < files.length; i++) {
|
||||
files[i] = getData(files[i], currDirectory, params.path);
|
||||
}
|
||||
|
||||
path = currDirectory;
|
||||
contents = files;
|
||||
date = fs.statSync(currDirectory).mtime;
|
||||
} else {
|
||||
path = currDirectory;
|
||||
contents = [];
|
||||
raw = true;
|
||||
|
||||
var extension = params.path.split('.').pop();
|
||||
var width, height;
|
||||
width = "calc(100vw - 100px)";
|
||||
if (extension == "png" || extension == "jpg") {
|
||||
var dimensions = sizeOf(currDirectory);
|
||||
width = dimensions.width + "px";
|
||||
height = dimensions.height;
|
||||
}
|
||||
if (extension == "sb3" || extension == "sjson") {
|
||||
width = "100vmin";
|
||||
}
|
||||
|
||||
date = fs.statSync(currDirectory).mtime;
|
||||
|
||||
return {
|
||||
body: {
|
||||
path, contents, raw: true, currPath: '/api/file/' + params.path,
|
||||
width: width, height: height + "px",
|
||||
extension: extension,
|
||||
date: date + "",
|
||||
isDark: isDark
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
return {
|
||||
path, contents, raw: false, currPath: '/api/file/' + params.path, width: "calc(100vw - 100px)", extension: 'none', date: date + "", isDark: isDark
|
||||
};
|
||||
|
||||
}
|
166
src/routes/data/[...path]/+page.svelte
Normal file
166
src/routes/data/[...path]/+page.svelte
Normal file
|
@ -0,0 +1,166 @@
|
|||
<script>
|
||||
import Main from "$lib/Main.svelte";
|
||||
import { page } from "$app/stores";
|
||||
import { goto } from "$app/navigation";
|
||||
import { browser } from "$app/environment";
|
||||
|
||||
/** @type {import('./$types').PageData} */
|
||||
export let data;
|
||||
|
||||
let {path, contents, raw, currPath, extension, width, height, date} = data;
|
||||
|
||||
var isDark = browser
|
||||
? localStorage.getItem("theme") == "dark"
|
||||
? "dark"
|
||||
: ""
|
||||
: "";
|
||||
</script>
|
||||
|
||||
<Main
|
||||
classes={isDark}
|
||||
textTop={path}
|
||||
download="/{currPath}"
|
||||
textBottom="File viewer by tdgmdev.net"
|
||||
turbowarp={extension == "sjson" || extension == "sb3"}
|
||||
>
|
||||
<div class="banner-mid" style="--width: {width}">
|
||||
{#if !raw}
|
||||
<table style="--width: 100%">
|
||||
<tr>
|
||||
<td>Name</td>
|
||||
<td>Modified on</td>
|
||||
<td>Download</td>
|
||||
<td>Special actions</td>
|
||||
</tr>
|
||||
{#each contents as content}
|
||||
<tr>
|
||||
<td
|
||||
><a href="{$page.url.pathname}/{content.link}"
|
||||
>{content.name}</a
|
||||
></td
|
||||
>
|
||||
<td><span>{content.mtime}</td>
|
||||
<td
|
||||
><a
|
||||
href="/api/file/{content.dir}"
|
||||
download={!content.extension ? `${currPath.split('/').pop()}.zip` : content.name}>Download</a
|
||||
></td
|
||||
>
|
||||
{#if content.extension == "sjson" || content.extension == "sb3"}
|
||||
<td
|
||||
><a
|
||||
href="https://turbowarp.org/editor?project_url=https://files.tdgmdev.net/api/file/{content.dir}"
|
||||
download={content.name}>TurboWarp</a
|
||||
></td
|
||||
>
|
||||
{/if}
|
||||
</tr>
|
||||
{/each}
|
||||
</table>
|
||||
{/if}
|
||||
|
||||
{#if raw}
|
||||
<table style="--width: {width}">
|
||||
<tr>
|
||||
<td>File Viewer</td>
|
||||
</tr>
|
||||
{#if extension == "sb3" || extension == "sjson"}
|
||||
<iframe
|
||||
src="https://turbowarp.org/embed?project_url=https://files.tdgmdev.net{currPath}"
|
||||
class="turbowarp"
|
||||
width="800px"
|
||||
height="600px"
|
||||
style="background-color:white; --width: {width}; --height: {height}"
|
||||
/>
|
||||
{/if}
|
||||
{#if extension != "sb3" && extension != "sjson"}
|
||||
<iframe
|
||||
src={currPath}
|
||||
class="file-{extension}"
|
||||
width="800px"
|
||||
height="800px"
|
||||
style="background-color:white; --width: {width}; --height: {height}"
|
||||
/>
|
||||
{/if}
|
||||
</table>
|
||||
{/if}
|
||||
</div>
|
||||
</Main>
|
||||
|
||||
<style>
|
||||
iframe {
|
||||
width: 100%;
|
||||
height: 98%;
|
||||
}
|
||||
|
||||
table .file-jpg,
|
||||
table .file-png {
|
||||
height: var(--height);
|
||||
}
|
||||
|
||||
.file-sb3 {
|
||||
display: none;
|
||||
}
|
||||
|
||||
table .turbowarp {
|
||||
height: 75vmin;
|
||||
}
|
||||
|
||||
.banner-entry {
|
||||
display: table-row;
|
||||
}
|
||||
|
||||
table {
|
||||
overflow-y: auto;
|
||||
overflow-x: auto;
|
||||
width: var(--width);
|
||||
max-width: 100vw;
|
||||
display: block;
|
||||
}
|
||||
|
||||
td {
|
||||
width: 200px;
|
||||
}
|
||||
|
||||
iframe {
|
||||
border: none;
|
||||
}
|
||||
|
||||
tr:not(:last-child) {
|
||||
border-bottom: solid var(--gray) 1px;
|
||||
}
|
||||
|
||||
tr:first-child {
|
||||
background-color: var(--blue);
|
||||
color: white;
|
||||
position: sticky;
|
||||
top: 0;
|
||||
}
|
||||
|
||||
tr {
|
||||
display: block;
|
||||
padding: 7px;
|
||||
}
|
||||
|
||||
a {
|
||||
text-decoration: none;
|
||||
color: var(--blue-again);
|
||||
}
|
||||
|
||||
.banner-mid {
|
||||
border: solid var(--gray) 1px;
|
||||
border-radius: 10px;
|
||||
}
|
||||
|
||||
.banner-mid {
|
||||
width: var(--width);
|
||||
font-size: 12px;
|
||||
max-height: 100%;
|
||||
display: flex;
|
||||
justify-content: space-around;
|
||||
height: 100%;
|
||||
overflow: auto;
|
||||
font-weight: normal;
|
||||
background: var(--white);
|
||||
}
|
||||
</style>
|
BIN
static/favicon.png
Normal file
BIN
static/favicon.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 1.5 KiB |
79
static/img/border.svg
Normal file
79
static/img/border.svg
Normal file
|
@ -0,0 +1,79 @@
|
|||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
width="92.684387mm"
|
||||
height="15.23604mm"
|
||||
viewBox="0 0 92.684385 15.23604"
|
||||
version="1.1"
|
||||
id="svg1110"
|
||||
sodipodi:docname="border.svg"
|
||||
inkscape:version="1.2.2 (b0a8486541, 2022-12-01)"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:svg="http://www.w3.org/2000/svg">
|
||||
<sodipodi:namedview
|
||||
id="namedview1112"
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1.0"
|
||||
inkscape:showpageshadow="2"
|
||||
inkscape:pageopacity="0.0"
|
||||
inkscape:pagecheckerboard="0"
|
||||
inkscape:deskcolor="#d1d1d1"
|
||||
inkscape:document-units="mm"
|
||||
showgrid="false"
|
||||
inkscape:zoom="1.5518659"
|
||||
inkscape:cx="273.54168"
|
||||
inkscape:cy="-22.231303"
|
||||
inkscape:window-width="1868"
|
||||
inkscape:window-height="1006"
|
||||
inkscape:window-x="24"
|
||||
inkscape:window-y="46"
|
||||
inkscape:window-maximized="1"
|
||||
inkscape:current-layer="layer1" />
|
||||
<defs
|
||||
id="defs1107" />
|
||||
<g
|
||||
inkscape:label="Layer 1"
|
||||
inkscape:groupmode="layer"
|
||||
id="layer1"
|
||||
transform="translate(-1.5551306,-179.57009)">
|
||||
<path
|
||||
id="rect1646"
|
||||
style="fill:#ffffff;fill-opacity:1;fill-rule:evenodd;stroke-width:15.875;stroke-linecap:round;stroke-linejoin:round;paint-order:stroke fill markers"
|
||||
d="m 1.5551306,187.34265 c 0,0 14.7844384,-7.77255 23.1710964,-7.77255 16.773316,0 29.568876,15.5451 46.342193,15.5451 8.386658,0 23.171094,-7.77255 23.171094,-7.77255 v 9.91277 H 1.5551306 Z"
|
||||
sodipodi:nodetypes="caacccc" />
|
||||
<circle
|
||||
style="fill:#ffffff;fill-opacity:1;fill-rule:evenodd;stroke-width:15.875;stroke-linecap:round;stroke-linejoin:round;paint-order:stroke fill markers"
|
||||
id="path1859"
|
||||
cx="62.078156"
|
||||
cy="185.98183"
|
||||
r="2.2243786" />
|
||||
<circle
|
||||
style="fill:#ffffff;fill-opacity:1;fill-rule:evenodd;stroke-width:15.875;stroke-linecap:round;stroke-linejoin:round;paint-order:stroke fill markers"
|
||||
id="circle1867"
|
||||
cx="72.732628"
|
||||
cy="184.888"
|
||||
r="3.4143901" />
|
||||
<circle
|
||||
style="fill:#ffffff;fill-opacity:1;fill-rule:evenodd;stroke-width:15.875;stroke-linecap:round;stroke-linejoin:round;paint-order:stroke fill markers"
|
||||
id="circle1869"
|
||||
cx="82.285164"
|
||||
cy="185.48705"
|
||||
r="1.2911379" />
|
||||
<circle
|
||||
style="fill:#ffffff;fill-opacity:1;fill-rule:evenodd;stroke-width:15.875;stroke-linecap:round;stroke-linejoin:round;paint-order:stroke fill markers"
|
||||
id="circle1871"
|
||||
cx="48.922638"
|
||||
cy="182.27203"
|
||||
r="1.2911379" />
|
||||
<circle
|
||||
style="fill:#ffffff;fill-opacity:1;fill-rule:evenodd;stroke-width:15.875;stroke-linecap:round;stroke-linejoin:round;paint-order:stroke fill markers"
|
||||
id="circle1873"
|
||||
cx="70.383842"
|
||||
cy="192.68364"
|
||||
r="0.87060106" />
|
||||
</g>
|
||||
</svg>
|
After Width: | Height: | Size: 3 KiB |
1
static/img/discord-mark-white.svg
Normal file
1
static/img/discord-mark-white.svg
Normal file
|
@ -0,0 +1 @@
|
|||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 127.14 96.36"><defs><style>.cls-1{fill:#222;}</style></defs><g id="图层_2" data-name="图层 2"><g id="Discord_Logos" data-name="Discord Logos"><g id="Discord_Logo_-_Large_-_White" data-name="Discord Logo - Large - White"><path class="cls-1" d="M107.7,8.07A105.15,105.15,0,0,0,81.47,0a72.06,72.06,0,0,0-3.36,6.83A97.68,97.68,0,0,0,49,6.83,72.37,72.37,0,0,0,45.64,0,105.89,105.89,0,0,0,19.39,8.09C2.79,32.65-1.71,56.6.54,80.21h0A105.73,105.73,0,0,0,32.71,96.36,77.7,77.7,0,0,0,39.6,85.25a68.42,68.42,0,0,1-10.85-5.18c.91-.66,1.8-1.34,2.66-2a75.57,75.57,0,0,0,64.32,0c.87.71,1.76,1.39,2.66,2a68.68,68.68,0,0,1-10.87,5.19,77,77,0,0,0,6.89,11.1A105.25,105.25,0,0,0,126.6,80.22h0C129.24,52.84,122.09,29.11,107.7,8.07ZM42.45,65.69C36.18,65.69,31,60,31,53s5-12.74,11.43-12.74S54,46,53.89,53,48.84,65.69,42.45,65.69Zm42.24,0C78.41,65.69,73.25,60,73.25,53s5-12.74,11.44-12.74S96.23,46,96.12,53,91.08,65.69,84.69,65.69Z"/></g></g></g></svg>
|
After Width: | Height: | Size: 986 B |
209
static/img/favicon.svg
Normal file
209
static/img/favicon.svg
Normal file
|
@ -0,0 +1,209 @@
|
|||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
width="636.23572"
|
||||
height="636.23572"
|
||||
viewBox="0 0 636.23571 636.2357"
|
||||
version="1.1"
|
||||
id="svg5"
|
||||
inkscape:version="1.2.2 (b0a8486541, 2022-12-01)"
|
||||
sodipodi:docname="favicon.svg"
|
||||
inkscape:export-filename="tdgmdev-banner2.png"
|
||||
inkscape:export-xdpi="192.05"
|
||||
inkscape:export-ydpi="192.05"
|
||||
xml:space="preserve"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"><sodipodi:namedview
|
||||
id="namedview7"
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1.0"
|
||||
inkscape:showpageshadow="2"
|
||||
inkscape:pageopacity="0.0"
|
||||
inkscape:pagecheckerboard="0"
|
||||
inkscape:deskcolor="#d1d1d1"
|
||||
inkscape:document-units="px"
|
||||
showgrid="false"
|
||||
inkscape:zoom="0.2570107"
|
||||
inkscape:cx="-254.8532"
|
||||
inkscape:cy="282.08942"
|
||||
inkscape:window-width="1868"
|
||||
inkscape:window-height="1006"
|
||||
inkscape:window-x="24"
|
||||
inkscape:window-y="46"
|
||||
inkscape:window-maximized="1"
|
||||
inkscape:current-layer="layer1" /><defs
|
||||
id="defs2"><filter
|
||||
inkscape:collect="always"
|
||||
style="color-interpolation-filters:sRGB"
|
||||
id="filter18739"
|
||||
x="-0.097691614"
|
||||
y="-0.097691614"
|
||||
width="1.1953832"
|
||||
height="1.1953832"><feGaussianBlur
|
||||
inkscape:collect="always"
|
||||
stdDeviation="1.3462276"
|
||||
id="feGaussianBlur18741" /></filter><filter
|
||||
inkscape:collect="always"
|
||||
style="color-interpolation-filters:sRGB"
|
||||
id="filter18743"
|
||||
x="-0.097691614"
|
||||
y="-0.097691614"
|
||||
width="1.1953832"
|
||||
height="1.1953832"><feGaussianBlur
|
||||
inkscape:collect="always"
|
||||
stdDeviation="1.3462276"
|
||||
id="feGaussianBlur18745" /></filter><filter
|
||||
inkscape:collect="always"
|
||||
style="color-interpolation-filters:sRGB"
|
||||
id="filter18751"
|
||||
x="-0.097691614"
|
||||
y="-0.097691614"
|
||||
width="1.1953832"
|
||||
height="1.1953832"><feGaussianBlur
|
||||
inkscape:collect="always"
|
||||
stdDeviation="1.3462276"
|
||||
id="feGaussianBlur18753" /></filter><filter
|
||||
inkscape:collect="always"
|
||||
style="color-interpolation-filters:sRGB"
|
||||
id="filter18747"
|
||||
x="-0.097691614"
|
||||
y="-0.097691614"
|
||||
width="1.1953832"
|
||||
height="1.1953832"><feGaussianBlur
|
||||
inkscape:collect="always"
|
||||
stdDeviation="1.3462276"
|
||||
id="feGaussianBlur18749" /></filter><filter
|
||||
inkscape:collect="always"
|
||||
style="color-interpolation-filters:sRGB"
|
||||
id="filter18721"
|
||||
x="-0.09455217"
|
||||
y="-0.094552167"
|
||||
width="1.1891043"
|
||||
height="1.1891043"><feGaussianBlur
|
||||
inkscape:collect="always"
|
||||
stdDeviation="1.4593209"
|
||||
id="feGaussianBlur18723" /></filter><filter
|
||||
inkscape:collect="always"
|
||||
style="color-interpolation-filters:sRGB"
|
||||
id="filter9926"
|
||||
x="-0.024739079"
|
||||
y="-0.11562142"
|
||||
width="1.0494782"
|
||||
height="1.2312428"><feGaussianBlur
|
||||
inkscape:collect="always"
|
||||
stdDeviation="11.624891"
|
||||
id="feGaussianBlur9928" /></filter></defs><g
|
||||
inkscape:label="Layer 1"
|
||||
inkscape:groupmode="layer"
|
||||
id="layer1"
|
||||
transform="translate(-571.99581,-304.73986)"><g
|
||||
aria-label="T"
|
||||
id="g5506"
|
||||
style="font-size:10.5833px;line-height:1.25;font-family:'Open Sans';-inkscape-font-specification:'Open Sans';fill:#95c7b9;fill-opacity:1;stroke:none;stroke-width:0.0328121;stroke-dasharray:none;stroke-opacity:1"
|
||||
transform="matrix(16.127163,0,0,16.127163,-1450.517,-704.52306)" /><g
|
||||
id="g8696-4"
|
||||
transform="matrix(8.7626449,0,0,8.7626449,55.238563,-130.00498)"
|
||||
style="stroke-width:0.431323"><circle
|
||||
style="fill:#ff0000;fill-opacity:0.5;stroke-width:1.14121;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:3.96999;paint-order:stroke fill markers;filter:url(#filter18739)"
|
||||
id="path18727-5"
|
||||
cx="-69.380829"
|
||||
cy="78.74015"
|
||||
r="16.536457"
|
||||
transform="rotate(-90)" /><circle
|
||||
style="fill:#80ff00;fill-opacity:0.5;stroke-width:1.14121;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:3.96999;paint-order:stroke fill markers;filter:url(#filter18743)"
|
||||
id="circle18733-0"
|
||||
cx="-69.380829"
|
||||
cy="111.81307"
|
||||
r="16.536457"
|
||||
transform="rotate(-90)" /><circle
|
||||
style="fill:#00ffff;fill-opacity:0.5;stroke-width:1.14121;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:3.96999;paint-order:stroke fill markers;filter:url(#filter18751)"
|
||||
id="circle18735-3"
|
||||
cx="-102.45375"
|
||||
cy="78.74015"
|
||||
r="16.536457"
|
||||
transform="rotate(-90)" /><circle
|
||||
style="fill:#8000ff;fill-opacity:0.5;stroke-width:1.14121;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:3.96999;paint-order:stroke fill markers;filter:url(#filter18747)"
|
||||
id="circle18737-6"
|
||||
cx="-102.45375"
|
||||
cy="111.81307"
|
||||
r="16.536457"
|
||||
transform="rotate(-90)" /><circle
|
||||
style="opacity:0.388158;fill:#80ff00;fill-opacity:0.5;stroke-width:1.14121;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:3.96999;paint-order:stroke fill markers"
|
||||
id="circle18757"
|
||||
cx="-69.380829"
|
||||
cy="111.81307"
|
||||
r="16.536457"
|
||||
transform="rotate(-90)" /><circle
|
||||
style="opacity:0.388158;fill:#00ffff;fill-opacity:0.5;stroke-width:1.14121;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:3.96999;paint-order:stroke fill markers"
|
||||
id="circle18759"
|
||||
cx="-102.45375"
|
||||
cy="78.74015"
|
||||
r="16.536457"
|
||||
transform="rotate(-90)" /><circle
|
||||
style="opacity:0.388158;fill:#8000ff;fill-opacity:0.5;stroke-width:1.14121;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:3.96999;paint-order:stroke fill markers"
|
||||
id="circle18761"
|
||||
cx="-102.45375"
|
||||
cy="111.81307"
|
||||
r="16.536457"
|
||||
transform="rotate(-90)" /><circle
|
||||
style="opacity:0.388158;fill:#ff0000;fill-opacity:0.5;stroke-width:1.14121;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:3.96999;paint-order:stroke fill markers"
|
||||
id="circle18755"
|
||||
cx="-69.380829"
|
||||
cy="78.74015"
|
||||
r="16.536457"
|
||||
transform="rotate(-90)" /><g
|
||||
id="g18719"
|
||||
style="fill:#ffffff;fill-opacity:1;stroke-width:0.431323;filter:url(#filter18721)"><path
|
||||
id="path18711"
|
||||
style="fill:#ffffff;fill-opacity:1;stroke-width:1.1412;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:3.96999;paint-order:stroke fill markers"
|
||||
d="m 91.969323,72.688126 3.307291,-5.291666 3.307292,5.291666 v 26.45833 l -3.307291,5.291674 -3.307292,-5.291674 z"
|
||||
sodipodi:nodetypes="ccccccc" /><path
|
||||
id="path18713"
|
||||
style="fill:#ffffff;fill-opacity:1;stroke-width:1.1412;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:3.96999;paint-order:stroke fill markers"
|
||||
d="m 108.50579,82.610006 5.29166,3.30729 -5.29166,3.30729 H 82.047448 l -5.291667,-3.30729 5.291667,-3.30729 z"
|
||||
sodipodi:nodetypes="ccccccc" /><path
|
||||
id="path18715"
|
||||
style="fill:#ffffff;fill-opacity:1;stroke-width:1.1412;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:3.96999;paint-order:stroke fill markers"
|
||||
d="m 102.29245,74.224251 6.08038,-1.403165 -1.40317,6.080382 -18.708871,18.708868 -6.080381,1.40317 1.403165,-6.08039 z"
|
||||
sodipodi:nodetypes="ccccccc" /><path
|
||||
id="path18717"
|
||||
style="fill:#ffffff;fill-opacity:1;stroke-width:1.1412;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:3.96999;paint-order:stroke fill markers"
|
||||
d="m 106.96966,92.933116 1.40317,6.08038 -6.08038,-1.40316 -18.708877,-18.708868 -1.403166,-6.080381 6.080382,1.403165 z"
|
||||
sodipodi:nodetypes="ccccccc" /></g><g
|
||||
id="g18709-1"
|
||||
style="fill:#ffffff;fill-opacity:1;stroke-width:0.431323"><path
|
||||
id="rect17499-0"
|
||||
style="fill:#ffffff;fill-opacity:1;stroke-width:1.1412;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:3.96999;paint-order:stroke fill markers"
|
||||
d="m 91.969323,72.688126 3.307291,-5.291666 3.307292,5.291666 v 26.45833 l -3.307291,5.291674 -3.307292,-5.291674 z"
|
||||
sodipodi:nodetypes="ccccccc" /><path
|
||||
id="path17521-6"
|
||||
style="fill:#ffffff;fill-opacity:1;stroke-width:1.1412;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:3.96999;paint-order:stroke fill markers"
|
||||
d="m 108.50579,82.610006 5.29166,3.30729 -5.29166,3.30729 H 82.047448 l -5.291667,-3.30729 5.291667,-3.30729 z"
|
||||
sodipodi:nodetypes="ccccccc" /><path
|
||||
id="path17515-3"
|
||||
style="fill:#ffffff;fill-opacity:1;stroke-width:1.1412;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:3.96999;paint-order:stroke fill markers"
|
||||
d="m 102.29245,74.224251 6.08038,-1.403165 -1.40317,6.080382 -18.708871,18.708868 -6.080381,1.40317 1.403165,-6.08039 z"
|
||||
sodipodi:nodetypes="ccccccc" /><path
|
||||
id="path17523-2"
|
||||
style="fill:#ffffff;fill-opacity:1;stroke-width:1.1412;stroke-linecap:round;stroke-linejoin:round;stroke-miterlimit:3.96999;paint-order:stroke fill markers"
|
||||
d="m 106.96966,92.933116 1.40317,6.08038 -6.08038,-1.40316 -18.708877,-18.708868 -1.403166,-6.080381 6.080382,1.403165 z"
|
||||
sodipodi:nodetypes="ccccccc" /></g></g><g
|
||||
aria-label="T"
|
||||
id="g5506-0"
|
||||
style="font-size:10.5833px;line-height:1.25;font-family:'Open Sans';-inkscape-font-specification:'Open Sans';fill:#95c7b9;fill-opacity:1;stroke:none;stroke-width:0.174407;stroke-dasharray:none;stroke-opacity:1"
|
||||
transform="matrix(11.467406,0,0,11.467406,-588.53565,-578.07927)" /><text
|
||||
xml:space="preserve"
|
||||
style="font-style:normal;font-variant:normal;font-weight:bold;font-stretch:normal;font-size:240.102px;line-height:1.25;font-family:monospace;-inkscape-font-specification:'monospace Bold';text-align:end;text-anchor:end;mix-blend-mode:normal;fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:25;stroke-linecap:round;stroke-linejoin:round;stroke-dasharray:none;stroke-opacity:1;paint-order:stroke fill markers;filter:url(#filter9926)"
|
||||
x="1047.2435"
|
||||
y="231.5193"
|
||||
id="text9924"
|
||||
transform="matrix(1.0004344,0,0,0.9995658,27.878782,278.56378)"><tspan
|
||||
sodipodi:role="line"
|
||||
style="font-style:normal;font-variant:normal;font-weight:bold;font-stretch:normal;font-family:monospace;-inkscape-font-specification:'monospace Bold';text-align:end;text-anchor:end;fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:25;stroke-linecap:round;stroke-linejoin:round;stroke-dasharray:none;stroke-opacity:1;paint-order:stroke fill markers"
|
||||
x="1047.2435"
|
||||
y="231.5193"
|
||||
id="tspan9922" /></text></g></svg>
|
After Width: | Height: | Size: 11 KiB |
1
static/img/github-mark-white.svg
Normal file
1
static/img/github-mark-white.svg
Normal file
|
@ -0,0 +1 @@
|
|||
<svg width="98" height="96" xmlns="http://www.w3.org/2000/svg"><path fill-rule="evenodd" clip-rule="evenodd" d="M48.854 0C21.839 0 0 22 0 49.217c0 21.756 13.993 40.172 33.405 46.69 2.427.49 3.316-1.059 3.316-2.362 0-1.141-.08-5.052-.08-9.127-13.59 2.934-16.42-5.867-16.42-5.867-2.184-5.704-5.42-7.17-5.42-7.17-4.448-3.015.324-3.015.324-3.015 4.934.326 7.523 5.052 7.523 5.052 4.367 7.496 11.404 5.378 14.235 4.074.404-3.178 1.699-5.378 3.074-6.6-10.839-1.141-22.243-5.378-22.243-24.283 0-5.378 1.94-9.778 5.014-13.2-.485-1.222-2.184-6.275.486-13.038 0 0 4.125-1.304 13.426 5.052a46.97 46.97 0 0 1 12.214-1.63c4.125 0 8.33.571 12.213 1.63 9.302-6.356 13.427-5.052 13.427-5.052 2.67 6.763.97 11.816.485 13.038 3.155 3.422 5.015 7.822 5.015 13.2 0 18.905-11.404 23.06-22.324 24.283 1.78 1.548 3.316 4.481 3.316 9.126 0 6.6-.08 11.897-.08 13.526 0 1.304.89 2.853 3.316 2.364 19.412-6.52 33.405-24.935 33.405-46.691C97.707 22 75.788 0 48.854 0z" fill="#222"/></svg>
|
After Width: | Height: | Size: 961 B |
10
svelte.config.js
Normal file
10
svelte.config.js
Normal file
|
@ -0,0 +1,10 @@
|
|||
import adapter from '@sveltejs/adapter-cloudflare';
|
||||
|
||||
/** @type {import('@sveltejs/kit').Config} */
|
||||
const config = {
|
||||
kit: {
|
||||
adapter: adapter()
|
||||
}
|
||||
};
|
||||
|
||||
export default config;
|
7
vite.config.js
Normal file
7
vite.config.js
Normal file
|
@ -0,0 +1,7 @@
|
|||
import { sveltekit } from '@sveltejs/kit/vite';
|
||||
|
||||
const config = {
|
||||
plugins: [sveltekit()]
|
||||
};
|
||||
|
||||
export default config;
|
Loading…
Reference in a new issue