Files
2026-05-10 18:22:19 +00:00

532 lines
16 KiB
HTML

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>GMMC WORLD ARCHIVES</title>
<link rel="preconnect" href="https://fonts.googleapis.com">
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link href="https://fonts.googleapis.com/css2?family=VT323&display=swap" rel="stylesheet">
<style>
:root {
--mc-bg: #111111;
--mc-ui-bg: #c6c6c6;
--mc-ui-dark: #373737;
--mc-ui-light: #ffffff;
--mc-ui-border: #000000;
--mc-text: #e0e0e0;
--mc-text-shadow: 2px 2px 0px #000000;
--mc-green: #55ff55;
--mc-gold: #ffaa00;
--mc-btn-bg: #8f8f8f;
--mc-btn-hover: #a0a0a0;
--mc-btn-shadow-light: #c6c6c6;
--mc-btn-shadow-dark: #505050;
}
* {
box-sizing: border-box;
}
body {
font-family: 'VT323', monospace;
background-color: var(--mc-bg);
background-image: url('/image.png');
background-size: cover;
background-position: center;
background-attachment: fixed;
color: var(--mc-text);
margin: 0;
padding: 24px;
line-height: 1.2;
font-size: 20px;
image-rendering: pixelated;
}
.container {
max-width: 900px;
margin: 0 auto;
background: rgba(17, 17, 17, 0.85);
padding: 2rem;
border: 4px solid #000;
box-shadow: inset 4px 4px 0px rgba(255, 255, 255, 0.15), inset -4px -4px 0px rgba(0, 0, 0, 0.6);
backdrop-filter: blur(2px);
}
h1 {
font-size: 3rem;
font-weight: 400;
margin: 0 0 1.5rem;
display: flex;
align-items: center;
gap: 1rem;
color: var(--mc-ui-light);
text-shadow: var(--mc-text-shadow);
text-transform: uppercase;
letter-spacing: 2px;
}
a {
color: var(--mc-gold);
text-decoration: none;
text-shadow: var(--mc-text-shadow);
}
a:hover {
color: var(--mc-green);
}
/* Stats Grid - Inventory Style */
.stats {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(200px, 1fr));
gap: 1rem;
margin-bottom: 2.5rem;
}
.stat-card {
background: rgba(33, 33, 33, 0.9);
padding: 1rem;
border: 2px solid #000;
box-shadow: inset 2px 2px 0px #444, inset -2px -2px 0px #111;
display: flex;
flex-direction: column;
align-items: center;
text-align: center;
}
.stat-value {
font-size: 2.5rem;
color: var(--mc-green);
text-shadow: var(--mc-text-shadow);
margin-bottom: 0.25rem;
}
.stat-label {
font-size: 1.2rem;
color: #aaaaaa;
text-shadow: 1px 1px 0 #000;
}
/* File List */
h2 {
font-size: 2rem;
font-weight: 400;
margin: 2rem 0 1rem;
color: var(--mc-ui-light);
text-shadow: var(--mc-text-shadow);
border-bottom: 2px solid #555;
padding-bottom: 0.5rem;
}
.file-list {
list-style: none;
padding: 0;
margin: 0;
display: grid;
gap: 1rem;
}
.file-item {
background: rgba(20, 20, 20, 0.9);
border: 2px solid #000;
box-shadow: inset 2px 2px 0px #3a3a3a, inset -2px -2px 0px #0a0a0a;
padding: 1rem;
display: grid;
grid-template-columns: 1fr auto;
gap: 0.5rem 1rem;
align-items: start;
position: relative;
}
.file-item:hover {
background: rgba(30, 30, 30, 0.95);
border-color: #555;
box-shadow: inset 2px 2px 0px #4a4a4a, inset -2px -2px 0px #1a1a1a;
}
/* 1. Name */
.file-name {
font-size: 1.5rem;
color: var(--mc-gold);
text-shadow: var(--mc-text-shadow);
grid-column: 1;
grid-row: 1;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}
/* 2. Meta (ID, Size) */
.file-meta {
font-size: 1.1rem;
color: #aaaaaa;
display: flex;
gap: 1rem;
align-items: center;
grid-column: 1;
grid-row: 2;
text-shadow: 1px 1px 0 #000;
}
.file-id {
color: #aaaaaa;
}
/* 3. Description */
.file-desc {
font-size: 1.2rem;
color: #cccccc;
grid-column: 1 / -1;
grid-row: 3;
margin-top: 0.5rem;
line-height: 1.4;
max-height: 3.2em;
overflow: hidden;
text-shadow: 1px 1px 0 #000;
}
.file-desc.expanded {
max-height: none;
}
/* 4. Download Button - Minecraft Style */
.download-btn {
grid-column: 2;
grid-row: 1;
background-color: var(--mc-btn-bg);
color: #fff;
text-decoration: none;
padding: 8px 16px;
font-size: 1.2rem;
text-shadow: 1px 1px 0 #333;
border: 2px solid #000;
box-shadow:
inset 2px 2px 0px var(--mc-btn-shadow-light),
inset -2px -2px 0px var(--mc-btn-shadow-dark);
cursor: pointer;
justify-self: end;
display: inline-flex;
align-items: center;
gap: 0.5rem;
transition: none;
/* No smooth transition for pixel feel */
}
.download-btn:hover {
background-color: var(--mc-btn-hover);
color: #ffffa0;
}
.download-btn:active {
box-shadow:
inset 2px 2px 0px var(--mc-btn-shadow-dark),
inset -2px -2px 0px var(--mc-btn-shadow-light);
transform: translateY(2px);
}
/* Hide original button container generated by backend */
.file-item>div:nth-of-type(4) {
display: none !important;
}
/* Hide original pre block */
.usage-pre {
display: none !important;
}
/* New Command Row Styles */
.command-container {
grid-column: 1 / -1;
grid-row: 5;
margin-top: 1rem;
display: flex;
flex-direction: column;
gap: 0.5rem;
}
.command-row {
display: flex;
align-items: center;
background: #000;
border: 2px solid #555;
padding: 0.5rem;
gap: 0.75rem;
}
.command-text {
font-family: 'VT323', monospace;
font-size: 1.2rem;
color: #fff;
flex: 1;
overflow-x: auto;
white-space: nowrap;
scrollbar-width: none;
}
.icon-btn {
background-color: var(--mc-btn-bg);
border: 2px solid #000;
box-shadow:
inset 2px 2px 0px var(--mc-btn-shadow-light),
inset -2px -2px 0px var(--mc-btn-shadow-dark);
color: #fff;
cursor: pointer;
padding: 4px;
display: flex;
align-items: center;
justify-content: center;
flex-shrink: 0;
width: 32px;
height: 32px;
}
.icon-btn:hover {
background-color: var(--mc-btn-hover);
}
.icon-btn:active {
box-shadow:
inset 2px 2px 0px var(--mc-btn-shadow-dark),
inset -2px -2px 0px var(--mc-btn-shadow-light);
}
.icon-btn.success {
background-color: #55ff55;
color: #000;
}
/* Description Toggle */
.desc-toggle {
grid-column: 1 / -1;
grid-row: 4;
justify-self: start;
font-size: 1.1rem;
color: var(--mc-green);
cursor: pointer;
padding: 2px 0;
text-shadow: 1px 1px 0 #000;
}
.desc-toggle:hover {
text-decoration: underline;
color: #fff;
}
/* Usage Example Section */
.usage-example {
background: #000;
color: #fff;
padding: 1rem;
border: 2px solid #555;
font-family: 'VT323', monospace;
font-size: 1.1rem;
overflow-x: auto;
}
.usage-example pre {
margin: 0;
}
@media (max-width: 640px) {
body {
padding: 12px;
font-size: 18px;
}
h1 {
font-size: 2rem;
margin-bottom: 1rem;
}
.stats {
grid-template-columns: 1fr;
gap: 0.75rem;
}
.stat-card {
padding: 0.75rem;
}
.stat-value {
font-size: 2rem;
}
.file-item {
grid-template-columns: 1fr;
gap: 0.75rem;
padding: 0.75rem;
}
.file-name {
grid-column: 1;
grid-row: 1;
font-size: 1.3rem;
}
.file-meta {
grid-column: 1;
grid-row: 2;
flex-wrap: wrap;
gap: 0.5rem;
font-size: 1rem;
}
.download-btn {
grid-column: 1;
grid-row: 3;
justify-self: stretch;
width: 100%;
justify-content: center;
padding: 12px;
margin-top: 0.5rem;
}
.file-desc {
grid-row: 4;
font-size: 1.1rem;
}
.desc-toggle {
grid-row: 5;
padding: 8px 0;
}
.command-container {
grid-row: 6;
}
.command-row {
flex-direction: column;
align-items: stretch;
padding: 0.75rem;
}
.command-text {
margin-bottom: 0.5rem;
width: 100%;
}
.icon-btn {
width: 100%;
height: 40px;
}
}
</style>
</head>
<body>
<div class="container">
<h1>GMMC WORLD ARCHIVES</h1>
<div class="stats">
<div class="stat-card">
<div class="stat-value">{FILE_COUNT}</div>
<div class="stat-label">Available Files</div>
</div>
<div class="stat-card">
<div class="stat-value">{TOTAL_SIZE}</div>
<div class="stat-label">Total Size</div>
</div>
</div>
<h2>Available Files</h2>
<ul class="file-list">
{FILE_LIST_ITEMS}
</ul>
<h2>Usage Examples</h2>
<div class="usage-example">
<pre># Download with cURL
curl -O {BASE_URL}/download/file_id</pre>
</div>
<p style="color: #777; font-size: 1rem; margin-top: 3rem; text-align: center; text-shadow: 1px 1px 0 #000;">
<a href="https://gmmc.sirblob.co/">Minecraft Club at George Mason University</a>
</p>
</div>
<script>
document.addEventListener('DOMContentLoaded', function () {
// Add 'More' toggle links for long descriptions
document.querySelectorAll('.file-desc').forEach(function (desc) {
if (desc.scrollHeight > desc.clientHeight + 2) {
const btn = document.createElement('span');
btn.className = 'desc-toggle';
btn.textContent = '[Show more]';
btn.addEventListener('click', function () {
const expanded = desc.classList.toggle('expanded');
btn.textContent = expanded ? '[Show less]' : '[Show more]';
});
if (desc.parentNode) {
desc.parentNode.insertBefore(btn, desc.nextSibling);
}
}
});
// Transform usage-pre into interactive rows
document.querySelectorAll('.usage-pre').forEach(pre => {
const text = pre.textContent.trim();
if (!text) return;
const lines = text.split('\n').filter(line => line.trim());
const container = document.createElement('div');
container.className = 'command-container';
lines.forEach(line => {
const row = document.createElement('div');
row.className = 'command-row';
const code = document.createElement('div');
code.className = 'command-text';
code.textContent = line;
const btn = document.createElement('button');
btn.className = 'icon-btn';
btn.title = 'Copy to clipboard';
// Use simple SVG icons that fit the pixel theme
btn.innerHTML = `<svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="3" stroke-linecap="square" stroke-linejoin="miter"><rect x="9" y="9" width="13" height="13"></rect><path d="M5 15H4a2 2 0 0 1-2-2V4a2 2 0 0 1 2-2h9a2 2 0 0 1 2-2v1"></path></svg>`;
btn.addEventListener('click', () => {
const copyText = line;
const copyToClipboard = (str) => {
if (navigator.clipboard && navigator.clipboard.writeText) {
return navigator.clipboard.writeText(str);
}
return new Promise((resolve, reject) => {
const ta = document.createElement('textarea');
ta.value = str;
document.body.appendChild(ta);
ta.select();
try { document.execCommand('copy'); resolve(); }
catch (err) { reject(err); }
document.body.removeChild(ta);
});
};
copyToClipboard(copyText).then(() => {
btn.innerHTML = `<svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="4" stroke-linecap="square" stroke-linejoin="miter"><polyline points="20 6 9 17 4 12"></polyline></svg>`;
btn.classList.add('success');
setTimeout(() => {
btn.innerHTML = `<svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="3" stroke-linecap="square" stroke-linejoin="miter"><rect x="9" y="9" width="13" height="13"></rect><path d="M5 15H4a2 2 0 0 1-2-2V4a2 2 0 0 1 2-2h9a2 2 0 0 1 2-2v1"></path></svg>`;
btn.classList.remove('success');
}, 1500);
});
});
row.appendChild(code);
row.appendChild(btn);
container.appendChild(row);
});
if (pre.parentNode) {
pre.parentNode.appendChild(container);
}
});
});
</script>
</body>
</html>