Skip to content

Commit

Permalink
Merge pull request #148 from Cytoid/dev
Browse files Browse the repository at this point in the history
Deploy 20240229
  • Loading branch information
Teages authored Feb 28, 2024
2 parents b962fe9 + 4309c73 commit 2731c55
Show file tree
Hide file tree
Showing 16 changed files with 2,027 additions and 1,259 deletions.
16 changes: 4 additions & 12 deletions components/Level/Leaderboard.vue
Original file line number Diff line number Diff line change
Expand Up @@ -61,9 +61,6 @@ watch(diffRankPage, async (val) => {
rankData.value = newRanking
realDiffRankPage.value = val
})
function setRankPage(val: number) {
diffRankPage.value = val
}
async function syncRanking() {
loadingRank.value = true
const ans = await useQuery(rankingQuery, {
Expand Down Expand Up @@ -152,7 +149,7 @@ interface chartData {
<tbody>
<tr
v-for="(rank, index) in rankData.chart.leaderboard" :key="index + realDiffRankPage * 10 - 9"
class="even:bg-neutral-focus border-b-0"
class="even:bg-[color-mix(in_oklab,oklch(var(--n)),black_7%)] border-b-0"
>
<th>#{{ index + realDiffRankPage * 10 - 9 }}</th>
<td class="text-sm">
Expand Down Expand Up @@ -221,16 +218,11 @@ interface chartData {
</NuxtLink>
<!-- Page Switch -->
<Pagination
<PaginationLite
v-if="rankData.chart?.numPlayers && rankData.chart?.numPlayers > 10"
v-model="diffRankPage"
:total="Math.ceil(rankData.chart?.numPlayers / 10)"
class="w-full justify-center sm:justify-end"
:page="diffRankPage"
:total-page="Math.ceil(rankData.chart?.numPlayers / 10)"
:to-first-page="() => { diffRankPage = 1 }"
:to-prev-page="() => { diffRankPage -= 1 }"
:to-next-page="() => { diffRankPage += 1 }"
:to-final-page="() => { if (rankData?.chart) { diffRankPage = Math.ceil(rankData.chart.numPlayers / 10) } }"
:jump-to-page="setRankPage"
/>
</div>
<div v-else>
Expand Down
148 changes: 97 additions & 51 deletions components/Pagination.vue
Original file line number Diff line number Diff line change
@@ -1,45 +1,86 @@
<script setup lang="ts">
const props = defineProps<{
toFirstPage: () => void
toPrevPage: () => void
toNextPage: () => void
toFinalPage: () => void
page: number
totalPage: number
const props = withDefaults(defineProps<{
total: number
max?: number
disabled?: boolean
}>(), {
max: 6,
disabled: false,
})
jumpToPage: (page: number) => void
const page = defineModel<number>({ required: true })
const total = computed(() => props.total)
isFirstPage?: boolean
isFinalPage?: boolean
const disabled = computed(() => !!props.disabled)
disabled?: boolean
}>()
const displayedPages = computed<Array<number | '...'>>(() => {
const total = props.total
const current = page.value
const pages = new Set<number>()
const _isFirstPage = computed(() => {
if (props.isFirstPage) {
return props.isFirstPage
}
if (props.page !== undefined && props.totalPage !== undefined) {
return props.page === 1
}
return false
})
pages.add(1)
pages.add(current)
pages.add(total)
const max = props.max - pages.size
const _isFinalPage = computed(() => {
if (props.isFinalPage) {
return props.isFinalPage
let addedPrev = current
let addedNext = current
for (let i = 0; i < max; i += 1) {
const can: Array<'prev' | 'next'> = []
if (addedPrev - 1 > 1) {
can.push('prev')
}
if (addedNext + 1 < total) {
can.push('next')
}
const prefer = i % 2 === 0 ? 'next' : 'prev'
const direction: 'prev' | 'next' | undefined = can.includes(prefer) ? prefer : can[0]
if (direction === 'prev') {
pages.add(addedPrev - 1)
addedPrev -= 1
}
else if (direction === 'next') {
pages.add(addedNext + 1)
addedNext += 1
}
else {
break
}
}
if (props.page !== undefined && props.totalPage !== undefined) {
return props.page === props.totalPage
const result: Array<number | '...'> = [...pages.values()].sort((a, b) => a - b)
// push '...' in non-sequential pages
let last = 1
for (let i = 0; i < result.length; i += 1) {
const p = result[i] as number
if (p - last > 1) {
result.splice(i, 0, '...')
i += 1
}
last = p
}
return false
return result
})
const open = ref(false)
const customPage = ref('')
function _jumpToPage() {
const _customPage = Number.parseInt(customPage.value) || 1
props.jumpToPage(_customPage)
function onClickPage(p: number) {
if (p === page.value) {
openJump()
}
else {
page.value = p
}
}
function openJump() {
customPage.value = page.value.toString()
open.value = true
}
function jumpToPage() {
page.value = Number.parseInt(customPage.value) || 1
open.value = false
customPage.value = ''
}
Expand All @@ -49,24 +90,29 @@ function _jumpToPage() {
<div class="flex">
<div v-if="!open" class="flex pt-4">
<div class="flex-1" />
<div class="join shadow-xl">
<button v-if="toFirstPage" class="join-item btn btn-neutral btn-sm" :disabled="_isFirstPage || disabled" @click="toFirstPage">
<Icon name="ic:round-keyboard-double-arrow-left" />
</button>
<button v-if="toPrevPage" class="join-item btn btn-neutral btn-sm" :disabled="_isFirstPage || disabled" @click="toPrevPage">
<div class="shadow-xl flex content-center items-center gap-2">
<!-- <button class="btn btn-neutral btn-sm btn-square" :disabled="isFirstPage || disabled" @click="page -= 1">
<Icon name="ic:round-keyboard-arrow-left" />
</button>
<button v-if="page" class="join-item btn font-bold btn-sm btn-primary" :disabled="disabled" @click="open = (jumpToPage != null)">
{{ page }}
<template v-if="totalPage">
/ {{ totalPage }}
</template>
</button>
<button v-if="toNextPage" class="join-item btn btn-neutral btn-sm" :disabled="_isFinalPage || disabled" @click="toNextPage">
</button> -->
<template v-for="p in displayedPages" :key="p">
<button
v-if="p !== '...'"
class="btn btn-sm"
:class="{
'btn-primary': p === page,
'btn-neutral': p !== page,
}"
:disabled="disabled"
@click="onClickPage(p)"
v-text="p"
/>
<span v-else class="select-none">...</span>
</template>
<!-- <button class="btn btn-neutral btn-sm btn-square" :disabled="isFinalPage || disabled" @click="page += 1">
<Icon name="ic:round-keyboard-arrow-right" />
</button>
<button v-if="toFinalPage" class="join-item btn btn-neutral btn-sm" :disabled="_isFinalPage || disabled" @click="toFinalPage">
<Icon name="ic:round-keyboard-double-arrow-right" />
</button> -->
<button class="btn btn-secondary btn-sm btn-circle" :disabled="disabled" @click="openJump">
<Icon name="uil:enter" />
</button>
</div>
</div>
Expand All @@ -77,14 +123,14 @@ function _jumpToPage() {
<Icon name="material-symbols:close" size="24" />
</button>
<input
v-model="customPage" type="number" :placeholder="page?.toString()" :min="1" :max="totalPage" class="join-item input input-sm text-center w-20 input-bordered appearance-none"
v-model="customPage" type="number" :placeholder="page?.toString()" :min="1" :max="total" class="join-item input input-sm text-center w-20 input-bordered appearance-none"
@keyup.enter="null"
>
<button v-if="totalPage" class="join-item btn btn-neutral w-20 font-bold btn-sm" :disabled="disabled" @click="customPage = totalPage.toString()">
/ {{ totalPage }}
<button class="join-item btn btn-neutral w-20 font-bold btn-sm" :disabled="disabled" @click="customPage = total.toString()">
/ {{ total }}
</button>
<button class="join-item btn btn-sm btn-primary btn-square" :disabled="disabled || customPage === ''" @click="_jumpToPage">
<Icon name="ic:twotone-keyboard-arrow-right" size="24" />
<button class="join-item btn btn-sm btn-primary btn-square" :disabled="disabled || customPage === ''" @click="jumpToPage">
<Icon name="uil:enter" size="24" />
</button>
</div>
</div>
Expand Down
72 changes: 72 additions & 0 deletions components/PaginationLite.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,72 @@
<script setup lang="ts">
const props = withDefaults(defineProps<{
total: number
max?: number
disabled?: boolean
}>(), {
max: 6,
disabled: false,
})
const page = defineModel<number>({ required: true })
const total = computed(() => props.total)
const disabled = computed(() => !!props.disabled)
const isFirstPage = computed(() => page.value === 1)
const isFinalPage = computed(() => page.value === total.value)
const open = ref(false)
const customPage = ref('')
function openJump() {
customPage.value = page.value.toString()
open.value = true
}
function jumpToPage() {
page.value = Number.parseInt(customPage.value) || 1
open.value = false
customPage.value = ''
}
</script>

<template>
<div class="flex">
<div v-if="!open" class="flex pt-4">
<div class="flex-1" />
<div class="join shadow-xl">
<button class="join-item btn btn-neutral btn-sm" :disabled="isFirstPage || disabled" @click="page = 1">
<Icon name="ic:round-keyboard-double-arrow-left" />
</button>
<button class="join-item btn btn-neutral btn-sm" :disabled="isFirstPage || disabled" @click="page -= 1">
<Icon name="ic:round-keyboard-arrow-left" />
</button>
<button v-if="page" class="join-item btn font-bold btn-sm btn-primary" :disabled="disabled" @click="openJump">
{{ page }} / {{ total }}
</button>
<button class="join-item btn btn-neutral btn-sm" :disabled="isFinalPage || disabled" @click="page += 1">
<Icon name="ic:round-keyboard-arrow-right" />
</button>
<button class="join-item btn btn-neutral btn-sm" :disabled="isFinalPage || disabled" @click="page = total">
<Icon name="ic:round-keyboard-double-arrow-right" />
</button>
</div>
</div>

<div v-else class="flex pt-4">
<div class="join text-base-content w-full flex">
<button class="join-item btn btn-error btn-sm btn-square" :disabled="disabled" @click="open = false">
<Icon name="material-symbols:close" size="24" />
</button>
<input
v-model="customPage" type="number" :placeholder="page?.toString()" :min="1" :max="total" class="join-item input input-sm text-center w-20 input-bordered appearance-none"
@keyup.enter="null"
>
<button class="join-item btn btn-neutral w-20 font-bold btn-sm" :disabled="disabled" @click="customPage = total.toString()">
/ {{ total }}
</button>
<button class="join-item btn btn-sm btn-primary btn-square" :disabled="disabled || customPage === ''" @click="jumpToPage">
<Icon name="ic:twotone-keyboard-arrow-right" size="24" />
</button>
</div>
</div>
</div>
</template>
62 changes: 48 additions & 14 deletions components/SearchBar/Record.vue
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import { RecordQuerySort } from '~/gql/graphql'
const route = useRoute()
const router = useRouter()
const { user } = useAuth()
const { user, isModerator } = useAuth()
const chartId = computed({
get() {
Expand Down Expand Up @@ -47,24 +47,26 @@ const endDate = computed({
const best = computed({
get() {
return route.query.best === 'true' ?? false
return route.query.best === 'true'
},
set(newVal) {
updateRouter({ best: newVal ? 'true' : undefined })
},
})
// const ranked = computed({
// get() {
// if (best.value) {
// return false
// }
// return route.query.ranked === 'false' ?? true
// },
// set(newVal) {
// updateRouter({ ranked: newVal ? 'false' : undefined })
// },
// })
const ranked = computed({
get() {
if (best.value || !isModerator.value) {
return true
}
// unless it is explicitly set to false
return route.query.ranked !== 'false'
},
set(newVal) {
console.log(newVal)
updateRouter({ ranked: newVal.toString() || undefined })
},
})
const order = computed({
get() {
Expand Down Expand Up @@ -214,9 +216,9 @@ async function updateRouter(val: LocationQueryRaw | undefined) {
</div>
</div>
<!-- Sort -->
<div class="w-full sm:flex">
<div class="sm:flex gap-4">
<!-- Sort -->
<div class="max-w-fit">
<p class="card-subtitle">
Sort
Expand Down Expand Up @@ -247,6 +249,7 @@ async function updateRouter(val: LocationQueryRaw | undefined) {
</div>
</div>
<!-- Is best -->
<div class="pt-4 sm:pt-0">
<p class="card-subtitle">
Best Record
Expand Down Expand Up @@ -275,6 +278,37 @@ async function updateRouter(val: LocationQueryRaw | undefined) {
</div>
</div>
</div>
<!-- Is ranked (admin only) -->
<div v-if="isModerator" class="pt-4 sm:pt-0">
<p class="card-subtitle">
Ranked
</p>
<div class="pt-4 sm:pt-0">
<div class="join pt-2">
<button
class="join-item btn"
:class="{
'btn-active btn-secondary': !ranked,
'btn-neutral': ranked,
}"
@click="ranked = false"
>
Practice
</button>
<button
class="join-item btn"
:class="{
'btn-active btn-primary': ranked,
'btn-neutral': !ranked,
}"
@click="ranked = true"
>
Ranked
</button>
</div>
</div>
</div>
</div>
</div>
</div>
Expand Down
Loading

0 comments on commit 2731c55

Please sign in to comment.