[c] progress on modlist page
This commit is contained in:
parent
7faed5af20
commit
77ff08f737
9 changed files with 175 additions and 62 deletions
|
@ -16,6 +16,7 @@
|
||||||
"@sveltejs/kit": "^1.20.5",
|
"@sveltejs/kit": "^1.20.5",
|
||||||
"sass": "^1.62.0",
|
"sass": "^1.62.0",
|
||||||
"svelte": "^3.54.0",
|
"svelte": "^3.54.0",
|
||||||
|
"svelte-material-icons": "^3.0.5",
|
||||||
"svelte-preprocess": "^5.0.3",
|
"svelte-preprocess": "^5.0.3",
|
||||||
"vite": "^4.3.0"
|
"vite": "^4.3.0"
|
||||||
},
|
},
|
||||||
|
|
68
src/app.scss
68
src/app.scss
|
@ -13,45 +13,11 @@ h1, h2, h3, h4, h5, h6, body {
|
||||||
// color: #000000;
|
// color: #000000;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Green Light scheme (Default) */
|
|
||||||
/* Can be forced with data-theme="light" */
|
|
||||||
[data-theme="light"],
|
[data-theme="light"],
|
||||||
:root:not([data-theme="dark"]) {
|
:root:not([data-theme="dark"]) {
|
||||||
--primary: #43a047;
|
|
||||||
--primary-hover: #388e3c;
|
|
||||||
--primary-focus: rgba(67, 160, 71, 0.125);
|
|
||||||
--primary-inverse: #FFF;
|
|
||||||
background-color: #FAF9F6;
|
background-color: #FAF9F6;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Green Dark scheme (Auto) */
|
|
||||||
/* Automatically enabled if user has Dark mode enabled */
|
|
||||||
@media only screen and (prefers-color-scheme: dark) {
|
|
||||||
:root:not([data-theme]) {
|
|
||||||
--primary: #43a047;
|
|
||||||
--primary-hover: #4caf50;
|
|
||||||
--primary-focus: rgba(67, 160, 71, 0.25);
|
|
||||||
--primary-inverse: #FFF;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Green Dark scheme (Forced) */
|
|
||||||
/* Enabled if forced with data-theme="dark" */
|
|
||||||
[data-theme="dark"] {
|
|
||||||
--primary: #43a047;
|
|
||||||
--primary-hover: #4caf50;
|
|
||||||
--primary-focus: rgba(67, 160, 71, 0.25);
|
|
||||||
--primary-inverse: #FFF;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Green (Common styles) */
|
|
||||||
:root {
|
|
||||||
--form-element-active-border-color: var(--primary);
|
|
||||||
--form-element-focus-color: var(--primary-focus);
|
|
||||||
--switch-color: var(--primary-inverse);
|
|
||||||
--switch-checked-background-color: var(--primary);
|
|
||||||
}
|
|
||||||
|
|
||||||
p, li {
|
p, li {
|
||||||
cursor: text;
|
cursor: text;
|
||||||
}
|
}
|
||||||
|
@ -60,3 +26,37 @@ article {
|
||||||
border-radius: 10px;
|
border-radius: 10px;
|
||||||
box-shadow: 0px 0px 15px rgba(32, 32, 32, 0.2);
|
box-shadow: 0px 0px 15px rgba(32, 32, 32, 0.2);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
[role="button"].card {
|
||||||
|
background-color: $zinc-100;
|
||||||
|
border-color: $zinc-50;
|
||||||
|
p {
|
||||||
|
color: black;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
button.transparent,
|
||||||
|
[role="button"].transparent {
|
||||||
|
--pico-background-color: var(--pico-form-element-background-color);
|
||||||
|
--pico-border-color: var(--pico-form-element-border-color);
|
||||||
|
border-left: none;
|
||||||
|
border-right: none;
|
||||||
|
color: black;
|
||||||
|
|
||||||
|
&:focus {
|
||||||
|
outline: none;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-theme="dark"] button.transparent,
|
||||||
|
[data-theme="dark"] [role="button"].transparent {
|
||||||
|
color: white;
|
||||||
|
}
|
||||||
|
|
||||||
|
[data-theme="dark"] [role="button"].card {
|
||||||
|
background-color: $slate-800;
|
||||||
|
border-color: $slate-750;
|
||||||
|
p {
|
||||||
|
color: white;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
15
src/lib/common.ts
Normal file
15
src/lib/common.ts
Normal file
|
@ -0,0 +1,15 @@
|
||||||
|
export function smoothScrollTo(elementId: string) {
|
||||||
|
const element = document.getElementById(elementId);
|
||||||
|
if (element) {
|
||||||
|
element.scrollIntoView({
|
||||||
|
behavior: 'smooth'
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export function handleKeydown(elementId: string, event: KeyboardEvent) {
|
||||||
|
// Trigger redirection on Enter key or Space bar
|
||||||
|
if (event.key === 'Enter' || event.key === ' ') {
|
||||||
|
smoothScrollTo(elementId);
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,10 +1,30 @@
|
||||||
<script>
|
<script>
|
||||||
import { onMount } from "svelte";
|
import { onMount } from "svelte";
|
||||||
|
import IconChevronDown from 'svelte-material-icons/ChevronDown.svelte';
|
||||||
|
import IconClose from 'svelte-material-icons/Close.svelte';
|
||||||
|
|
||||||
let mods = { mods: [], optional_mods: [] };
|
let mods = { mods: [], optional_mods: [] };
|
||||||
|
let timeout;
|
||||||
let searchQuery = "";
|
let searchQuery = "";
|
||||||
let selectedFile = "modlist-rekindled.json";
|
let selectedFile = "modlist-rekindled.json";
|
||||||
let fileList = [];
|
let fileList = [];
|
||||||
|
|
||||||
|
let searchQueryInput = (event) => {
|
||||||
|
clearTimeout(timeout);
|
||||||
|
timeout = setTimeout(checkOverflow, 0);
|
||||||
|
};
|
||||||
|
|
||||||
|
function checkOverflow() {
|
||||||
|
const modCards = document.querySelectorAll('.mod-card');
|
||||||
|
modCards.forEach((modCard) => {
|
||||||
|
if (modCard.scrollHeight > modCard.offsetHeight) {
|
||||||
|
modCard.style.backgroundColor = 'red';
|
||||||
|
} else {
|
||||||
|
modCard.style.backgroundColor = '';
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
async function fetchData(file) {
|
async function fetchData(file) {
|
||||||
const response = await fetch(`/assets/json/${file}`);
|
const response = await fetch(`/assets/json/${file}`);
|
||||||
const data = await response.json();
|
const data = await response.json();
|
||||||
|
@ -16,6 +36,7 @@
|
||||||
const data = await response.json();
|
const data = await response.json();
|
||||||
fileList = data;
|
fileList = data;
|
||||||
await fetchData(selectedFile);
|
await fetchData(selectedFile);
|
||||||
|
checkOverflow(); // Run checkOverflow once the component has mounted
|
||||||
});
|
});
|
||||||
|
|
||||||
function fuzzySearch(query, mods) {
|
function fuzzySearch(query, mods) {
|
||||||
|
@ -25,6 +46,12 @@
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function clearInput() {
|
||||||
|
clearTimeout(timeout);
|
||||||
|
timeout = setTimeout(checkOverflow, 0);
|
||||||
|
searchQuery = "";
|
||||||
|
}
|
||||||
|
|
||||||
function handleFileChange(event) {
|
function handleFileChange(event) {
|
||||||
selectedFile = event.target.value;
|
selectedFile = event.target.value;
|
||||||
fetchData(selectedFile);
|
fetchData(selectedFile);
|
||||||
|
@ -32,13 +59,17 @@
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<div class="search-container" role="group">
|
<div class="search-container" role="group">
|
||||||
<input type="search" placeholder="Search the mod-verse..." bind:value={searchQuery} />
|
<input type="search" placeholder="Search the mod-verse..." bind:value={searchQuery} on:input={searchQueryInput} />
|
||||||
|
<button class="close transparent" on:click={() => clearInput()}><IconClose size="1em" /></button>
|
||||||
<select bind:value={selectedFile} on:change={handleFileChange}>
|
<select bind:value={selectedFile} on:change={handleFileChange}>
|
||||||
{#each fileList as file}
|
{#each fileList as file}
|
||||||
<option value={file.file}>{file.name}</option>
|
<option value={file.file}>{file.name}</option>
|
||||||
{/each}
|
{/each}
|
||||||
</select>
|
</select>
|
||||||
</div>
|
</div>
|
||||||
|
<div class="scroll-to-optional">
|
||||||
|
<a href="#optional-mods"><IconChevronDown size="1.2em" /> View Optional Mods</a>
|
||||||
|
</div>
|
||||||
|
|
||||||
<hr />
|
<hr />
|
||||||
|
|
||||||
|
@ -50,7 +81,7 @@
|
||||||
{#each fuzzySearch(searchQuery, mods.mods).slice(index * 3, (index + 1) * 3) as mod}
|
{#each fuzzySearch(searchQuery, mods.mods).slice(index * 3, (index + 1) * 3) as mod}
|
||||||
<a
|
<a
|
||||||
role="button"
|
role="button"
|
||||||
class="mod-card contrast invert"
|
class="mod-card card contrast"
|
||||||
href={mod.link}
|
href={mod.link}
|
||||||
target="_blank"
|
target="_blank"
|
||||||
rel="noopener noreferrer"
|
rel="noopener noreferrer"
|
||||||
|
@ -73,7 +104,7 @@
|
||||||
{#each fuzzySearch(searchQuery, mods.optional_mods).slice(index * 3, (index + 1) * 3) as mod}
|
{#each fuzzySearch(searchQuery, mods.optional_mods).slice(index * 3, (index + 1) * 3) as mod}
|
||||||
<a
|
<a
|
||||||
role="button"
|
role="button"
|
||||||
class="mod-card contrast"
|
class="mod-card card contrast"
|
||||||
href={mod.link}
|
href={mod.link}
|
||||||
target="_blank"
|
target="_blank"
|
||||||
rel="noopener noreferrer"
|
rel="noopener noreferrer"
|
||||||
|
@ -98,13 +129,6 @@
|
||||||
gap: 1em;
|
gap: 1em;
|
||||||
}
|
}
|
||||||
|
|
||||||
.grid-item {
|
|
||||||
display: flex;
|
|
||||||
flex-direction: column;
|
|
||||||
align-items: center;
|
|
||||||
padding: 1em;
|
|
||||||
}
|
|
||||||
|
|
||||||
.search-container {
|
.search-container {
|
||||||
display: flex;
|
display: flex;
|
||||||
|
|
||||||
|
@ -112,13 +136,30 @@
|
||||||
width: 40%;
|
width: 40%;
|
||||||
border-radius: 0px 1000px 1000px 0px;
|
border-radius: 0px 1000px 1000px 0px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
button.close {
|
||||||
|
padding: 0 1em 0 1em;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.scroll-to-optional {
|
||||||
|
width: 100%;
|
||||||
|
text-align: right;
|
||||||
|
a {
|
||||||
|
text-decoration: none;
|
||||||
|
&:hover {
|
||||||
|
text-decoration: underline;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.mod-card {
|
.mod-card {
|
||||||
display: flex;
|
display: flex;
|
||||||
justify-content: center;
|
justify-content: center;
|
||||||
align-items: center;
|
// align-items: center;
|
||||||
padding: 0.5em 1em 0.5em 1em;
|
padding: 0.5em 1em 0.5em 1em;
|
||||||
|
height: 6em;
|
||||||
|
overflow: hidden;
|
||||||
|
|
||||||
img.mod-card-logo {
|
img.mod-card-logo {
|
||||||
height: 4em;
|
height: 4em;
|
||||||
|
@ -126,6 +167,7 @@
|
||||||
margin-right: 1em;
|
margin-right: 1em;
|
||||||
border-radius: 8px;
|
border-radius: 8px;
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
|
align-self: center;
|
||||||
}
|
}
|
||||||
|
|
||||||
.mod-card-text-ct {
|
.mod-card-text-ct {
|
||||||
|
@ -143,3 +185,4 @@
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|
||||||
|
|
|
@ -1,9 +1,36 @@
|
||||||
<script>
|
<script>
|
||||||
import "../app.scss";
|
import "../app.scss";
|
||||||
import Header from "./Header.svelte";
|
import Header from "./Header.svelte";
|
||||||
|
import { smoothScrollTo, handleKeydown } from "$lib/common";
|
||||||
|
|
||||||
import { fly } from 'svelte/transition'
|
import { fly } from "svelte/transition";
|
||||||
export let data
|
import { onMount } from "svelte";
|
||||||
|
export let data;
|
||||||
|
|
||||||
|
onMount(() => {
|
||||||
|
function smoothScrollTo(elementId) {
|
||||||
|
document.getElementById(elementId).scrollIntoView({
|
||||||
|
behavior: 'smooth'
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
function handleKeydown(elementId, event) {
|
||||||
|
if (event.key === 'Enter') {
|
||||||
|
smoothScrollTo(elementId);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function toggleTopButton() {
|
||||||
|
const topButton = document.querySelector('.top-button');
|
||||||
|
if (window.scrollY >= window.innerHeight) {
|
||||||
|
topButton.classList.add('show');
|
||||||
|
} else {
|
||||||
|
topButton.classList.remove('show');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
window.addEventListener('scroll', toggleTopButton);
|
||||||
|
})
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<div class="app">
|
<div class="app">
|
||||||
|
@ -18,14 +45,29 @@
|
||||||
</main>
|
</main>
|
||||||
{/key}
|
{/key}
|
||||||
|
|
||||||
|
<!-- svelte-ignore a11y-missing-attribute -->
|
||||||
|
<a
|
||||||
|
role="button"
|
||||||
|
tabindex="0"
|
||||||
|
class="top-button"
|
||||||
|
on:click={() => smoothScrollTo("header")}
|
||||||
|
on:keydown={(event) => handleKeydown("header", event)}
|
||||||
|
>
|
||||||
|
Top
|
||||||
|
</a>
|
||||||
|
|
||||||
<footer>
|
<footer>
|
||||||
<p>
|
<p>
|
||||||
© Sangelo & LogolicusZ, 2023-2024 | <a href="https://gitpot.org/ExploreCraft/website"> Source Code</a>
|
© Sangelo & LogolicusZ, 2023-2024 | <a
|
||||||
|
href="https://gitpot.org/ExploreCraft/website"
|
||||||
|
>
|
||||||
|
Source Code</a
|
||||||
|
>
|
||||||
</p>
|
</p>
|
||||||
</footer>
|
</footer>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<style>
|
<style lang="scss">
|
||||||
.app {
|
.app {
|
||||||
display: flex;
|
display: flex;
|
||||||
flex-direction: column;
|
flex-direction: column;
|
||||||
|
@ -55,6 +97,17 @@
|
||||||
font-weight: normal;
|
font-weight: normal;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.top-button {
|
||||||
|
display: none;
|
||||||
|
position: fixed;
|
||||||
|
bottom: 1em;
|
||||||
|
right: 1em;
|
||||||
|
|
||||||
|
&.show {
|
||||||
|
display: inline-block;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@media (min-width: 480px) {
|
@media (min-width: 480px) {
|
||||||
footer {
|
footer {
|
||||||
padding: 0.1em 0;
|
padding: 0.1em 0;
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
import Switcher from './Switcher.svelte';
|
import Switcher from './Switcher.svelte';
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<div class="header-container">
|
<div class="header-container" id="header">
|
||||||
<a class="link contrast" href="/">
|
<a class="link contrast" href="/">
|
||||||
<div class="header">
|
<div class="header">
|
||||||
<img class="logo" src="/assets/logo/explorecraft.svg" alt="ExploreCraft Logo" />
|
<img class="logo" src="/assets/logo/explorecraft.svg" alt="ExploreCraft Logo" />
|
||||||
|
|
|
@ -19,14 +19,3 @@
|
||||||
<p>Please report any missing mods on our <a href="https://discord.gg/Z2YehhEUVr" target="_blank" rel="noopener noreferrer">Discord</a>.</p>
|
<p>Please report any missing mods on our <a href="https://discord.gg/Z2YehhEUVr" target="_blank" rel="noopener noreferrer">Discord</a>.</p>
|
||||||
|
|
||||||
<ModCards />
|
<ModCards />
|
||||||
|
|
||||||
<style lang="scss">
|
|
||||||
.grid {
|
|
||||||
width: 100%;
|
|
||||||
}
|
|
||||||
|
|
||||||
.column {
|
|
||||||
width: 50%;
|
|
||||||
float: left;
|
|
||||||
}
|
|
||||||
</style>
|
|
||||||
|
|
|
@ -1,2 +1,9 @@
|
||||||
/* Variables and mixins declared here will be available in all other SCSS files */ /* https://github.com/picocss/pico/issues/201 */
|
/* Variables and mixins declared here will be available in all other SCSS files */ /* https://github.com/picocss/pico/issues/201 */
|
||||||
$semantic-root-element: "body div:first-child";
|
$semantic-root-element: "body div:first-child";
|
||||||
|
|
||||||
|
// colors
|
||||||
|
$zinc-50: #F0F1F3;
|
||||||
|
$zinc-100: #E0E3E7;
|
||||||
|
|
||||||
|
$slate-800: #2A3140;
|
||||||
|
$slate-750: #333C4E;
|
||||||
|
|
|
@ -773,6 +773,11 @@ svelte-hmr@^0.15.3:
|
||||||
resolved "https://registry.yarnpkg.com/svelte-hmr/-/svelte-hmr-0.15.3.tgz#df54ccde9be3f091bf5f18fc4ef7b8eb6405fbe6"
|
resolved "https://registry.yarnpkg.com/svelte-hmr/-/svelte-hmr-0.15.3.tgz#df54ccde9be3f091bf5f18fc4ef7b8eb6405fbe6"
|
||||||
integrity sha512-41snaPswvSf8TJUhlkoJBekRrABDXDMdpNpT2tfHIv4JuhgvHqLMhEPGtaQn0BmbNSTkuz2Ed20DF2eHw0SmBQ==
|
integrity sha512-41snaPswvSf8TJUhlkoJBekRrABDXDMdpNpT2tfHIv4JuhgvHqLMhEPGtaQn0BmbNSTkuz2Ed20DF2eHw0SmBQ==
|
||||||
|
|
||||||
|
svelte-material-icons@^3.0.5:
|
||||||
|
version "3.0.5"
|
||||||
|
resolved "https://registry.yarnpkg.com/svelte-material-icons/-/svelte-material-icons-3.0.5.tgz#37bed05ceadd981b0da8630bd43b6d7cd6345376"
|
||||||
|
integrity sha512-UbhAa+Btd5y6e6DMljVccP+cbJ8lvesltMippiCOvfIUtYe2TsQqM+P6osfrVsZHV47b1tY6AmqCuSpMKnwMOQ==
|
||||||
|
|
||||||
svelte-preprocess@^5.0.3:
|
svelte-preprocess@^5.0.3:
|
||||||
version "5.1.4"
|
version "5.1.4"
|
||||||
resolved "https://registry.yarnpkg.com/svelte-preprocess/-/svelte-preprocess-5.1.4.tgz#14ada075c94bbd2b71c5ec70ff72f8ebe1c95b91"
|
resolved "https://registry.yarnpkg.com/svelte-preprocess/-/svelte-preprocess-5.1.4.tgz#14ada075c94bbd2b71c5ec70ff72f8ebe1c95b91"
|
||||||
|
|
Loading…
Reference in a new issue