mods page impovements

This commit is contained in:
Hassaan Ali 2025-06-01 22:59:23 +05:00
parent 199d83f25c
commit a8151a3c0c

View file

@ -1,5 +1,6 @@
---
import { icon, library } from '@fortawesome/fontawesome-svg-core'
import ChevronDownIcon from '~/icons/ChevronDownIcon.astro'
import { faSort, faSortDown, faSortUp } from '@fortawesome/free-solid-svg-icons'
import { type ZenTheme } from '~/mods'
import { getPath, type Locale } from '~/utils/i18n'
@ -40,14 +41,16 @@ const totalPages = Math.ceil(allMods.length / defaultLimit)
/>
</div>
<div class="grid w-full grid-cols-2 place-items-center gap-4 sm:grid-cols-3">
<div
class="grid w-full auto-cols-max grid-cols-[auto,auto,1fr] place-items-center gap-4 sm:grid-cols-[auto,auto,1fr]"
>
<div class="flex flex-col items-start gap-2">
<button
class="text-md flex items-center gap-2 px-4 py-2 font-semibold"
class="flex items-center gap-2 rounded-full border border-subtle px-5 py-1 text-sm font-semibold shadow-sm transition-colors hover:bg-muted focus:bg-coral/10 sm:text-base"
id="created-sort"
type="button"
>
{translations.sort.lastCreated}
<span>{translations.sort.lastCreated}</span>
<span class="relative">
<span id="created-sort-default" class="" set:html={defaultSortIcon.html[0]} />
<span id="created-sort-asc" class="hidden" set:html={ascSortIcon.html[0]} />
@ -56,13 +59,13 @@ const totalPages = Math.ceil(allMods.length / defaultLimit)
</button>
</div>
<div class="flex flex-col items-center gap-2">
<div class="flex flex-col items-start gap-2">
<button
class="text-md flex items-center gap-2 px-4 py-2 font-semibold"
class="flex items-center gap-2 rounded-full border border-subtle px-5 py-1 text-sm font-semibold shadow-sm transition-colors hover:bg-muted focus:bg-coral/10 sm:text-base"
id="updated-sort"
type="button"
>
{translations.sort.lastUpdated}
<span>{translations.sort.lastUpdated}</span>
<span class="relative">
<span id="updated-sort-default" class="" set:html={defaultSortIcon.html[0]} />
<span id="updated-sort-asc" class="hidden" set:html={ascSortIcon.html[0]} />
@ -71,16 +74,42 @@ const totalPages = Math.ceil(allMods.length / defaultLimit)
</button>
</div>
<div class="col-span-2 flex items-center gap-2 px-4 py-2 sm:col-span-1">
<label class="text-md font-semibold" for="limit">
<div class="hidden items-center gap-2 sm:block">
<label class="text-md text-md font-semibold" for="limit-button">
{translations.sort.perPage}
</label>
<select class="rounded border border-dark px-2 py-1 text-sm dark:bg-paper" id="limit">
<option value="12">12</option>
<option value="24">24</option>
<option value="48">48</option>
<option value="96">96</option>
</select>
<div class="relative inline-block">
<button
id="limit-button"
type="button"
class="group flex min-w-[60px] items-center justify-between rounded border border-dark bg-paper px-2 py-1 text-sm dark:bg-paper"
aria-haspopup="true"
aria-expanded="false"
>
<span id="limit-value">12</span>
<ChevronDownIcon
class="size-4 transform transition-transform duration-200 group-open:rotate-180 md:ml-2"
/>
</button>
<div
id="limit-dropdown"
class="absolute right-0 mt-1 hidden w-full rounded border border-dark bg-paper py-1 shadow-lg"
role="menu"
>
{
[12, 24, 48, 96].map(value => (
<button
type="button"
class="block w-full px-2 py-1 text-left text-sm hover:bg-muted"
role="menuitem"
data-value={value}
>
{value}
</button>
))
}
</div>
</div>
</div>
</div>
</div>
@ -309,6 +338,13 @@ const totalPages = Math.ceil(allMods.length / defaultLimit)
}
})
}
document.addEventListener('limit-changed', e => {
if (e instanceof CustomEvent) {
const newLimit = e.detail.value
this.setState({ limit: newLimit, page: 1 })
}
})
}
setState(newState) {
// Prevent multiple renders
@ -676,4 +712,60 @@ const totalPages = Math.ceil(allMods.length / defaultLimit)
// Initialize the mods search
new ModsSearch()
class CustomDropdown {
constructor() {
this.button = document.getElementById('limit-button')
this.dropdown = document.getElementById('limit-dropdown')
this.valueSpan = document.getElementById('limit-value')
if (!this.button || !this.dropdown || !this.valueSpan) return
this.button.addEventListener('click', () => this.toggle())
this.dropdown.addEventListener('click', e => this.handleOptionClick(e))
// Close dropdown when clicking outside
document.addEventListener('click', e => {
if (!this.button?.contains(e.target) && !this.dropdown?.contains(e.target)) {
this.close()
}
})
}
toggle() {
const isExpanded = this.button?.getAttribute('aria-expanded') === 'true'
if (isExpanded) {
this.close()
} else {
this.open()
}
}
open() {
this.button?.setAttribute('aria-expanded', 'true')
this.dropdown?.classList.remove('hidden')
}
close() {
this.button?.setAttribute('aria-expanded', 'false')
this.dropdown?.classList.add('hidden')
}
handleOptionClick(e) {
const target = e.target
if (target instanceof HTMLButtonElement && target.dataset.value) {
const value = target.dataset.value
if (this.valueSpan) {
this.valueSpan.textContent = value
}
// Trigger change event for ModsSearch
const event = new CustomEvent('limit-changed', { detail: { value: parseInt(value, 10) } })
document.dispatchEvent(event)
this.close()
}
}
}
// Initialize the custom dropdown
new CustomDropdown()
</script>