Skip to content
Snippets Groups Projects
Commit 625ede2d authored by ForkBench's avatar ForkBench
Browse files

Adding paging : ability to select a competition and manage it.

parent 9c9e6458
No related branches found
No related tags found
No related merge requests found
<script lang="ts"> <script lang="ts">
import { onMount } from "svelte"; import { onMount } from "svelte";
import NavBar from "./common/NavBar.svelte";
import NavBar from "./components/NavBar.svelte"; import Registrations from "./components/Seedings/Registrations.svelte";
import Registrations from "./components/Registrations.svelte";
import * as Session from "../bindings/changeme/astro/services/session"; import * as Session from "../bindings/changeme/astro/services/session";
import { Competition } from "../bindings/changeme/astro/services/models"; import { Competition } from "../bindings/changeme/astro/services/models";
import NewPlayerForm from "./components/NewPlayerForm.svelte";
let competitions: Competition[] = []; let competitions: Competition[] = [];
let loading = true;
let competitionID = 0;
onMount(async () => { onMount(async () => {
competitions = await Session.GetCompetitions(); competitions = await Session.GetCompetitions();
loading = false;
}); });
</script> </script>
<div class="container"> <div class="container">
<NavBar /> <NavBar />
<NewPlayerForm /> <!-- Get competition ID -->
<!-- {#if competitions.length <= competitionID} {#if loading}
<p>Loading...</p> <p>Loading...</p>
{:else if competitions.length > 0}
<Registrations />
{:else} {:else}
<Registrations competition={competitions[competitionID]} /> <p>No competitions available or invalid competition ID.</p>
{/if} --> {/if}
</div> </div>
<style> <style>
......
...@@ -7,6 +7,7 @@ ...@@ -7,6 +7,7 @@
RemoveCompetition, RemoveCompetition,
} from "../../bindings/changeme/astro/services/session"; } from "../../bindings/changeme/astro/services/session";
import { onMount } from "svelte"; import { onMount } from "svelte";
import { SelectedCompetition } from "../store";
let competitions: Competition[] = []; let competitions: Competition[] = [];
...@@ -19,16 +20,23 @@ ...@@ -19,16 +20,23 @@
<div class="nav-bar"> <div class="nav-bar">
<div class="competition-container"> <div class="competition-container">
<!-- svelte-ignore a11y-no-static-element-interactions -->
{#each competitions as competition} {#each competitions as competition}
<!-- svelte-ignore a11y-click-events-have-key-events -->
<div <div
class="competition-el" class="competition-el"
style="background-color: {randomColor(rightBrighness)};" style="background-color: {randomColor(rightBrighness)};"
on:click={() => {
SelectedCompetition.set(competition);
}}
> >
<span>{competition.CompetitionName}</span> <span>{competition.CompetitionName}</span>
<button <button
on:click={async () => { on:click={async () => {
await RemoveCompetition(competition.CompetitionID); await RemoveCompetition(competition.CompetitionID);
loadCompetitions(); loadCompetitions();
SelectedCompetition.set(undefined);
}}>X</button }}>X</button
> >
</div> </div>
......
<script lang="ts">
import { onMount } from "svelte";
import * as Models from "../../bindings/changeme/astro/services/models";
import * as Session from "../../bindings/changeme/astro/services/session";
import swal from "sweetalert";
export let competition: Models.Competition;
let players: (Models.Player | null)[] = [];
let filteredPlayers: (Models.Player | null)[] = [];
async function loadPlayers() {
Session.GetAllPlayersFromCompetition(competition.CompetitionID).then(
(result) => {
players = result;
}
);
}
onMount(async () => {
await loadPlayers();
});
function getPlayerValueByKey(player: Models.Player | null, key: string) {
if (player === null) {
return "";
}
switch (key) {
case "PlayerInitialRank":
return player.PlayerInitialRank;
case "PlayerFirstname":
return player.PlayerFirstname;
case "PlayerLastname":
return player.PlayerLastname;
case "PlayerClub":
return player.PlayerClub;
default:
return "";
}
}
let sortBy = { key: "PlayerInitialRank", asc: true };
$: players = players.sort((a, b) => {
let aValue = getPlayerValueByKey(a, sortBy.key);
let bValue = getPlayerValueByKey(b, sortBy.key);
if (aValue === null || bValue === null) {
return 0;
}
if (aValue < bValue) {
return sortBy.asc ? -1 : 1;
}
if (aValue > bValue) {
return sortBy.asc ? 1 : -1;
}
return 0;
});
let searchTerms = "";
$: filteredPlayers = players.filter((player) => {
if (player === null) {
return [];
}
return (
player.PlayerFirstname.toLowerCase().includes(
searchTerms.toLowerCase()
) ||
player.PlayerLastname.toLowerCase().includes(
searchTerms.toLowerCase()
) ||
player.PlayerClub?.club_name
.toLowerCase()
.includes(searchTerms.toLowerCase())
);
});
</script>
<div class="registration-container">
<input
type="text"
bind:value={searchTerms}
placeholder="Search for a player"
/>
<table>
<thead>
<tr>
<th
on:click={() => {
sortBy = { key: "PlayerInitialRank", asc: !sortBy.asc };
}}>Initial Rank</th
>
<th
on:click={() => {
sortBy = { key: "PlayerFirstname", asc: !sortBy.asc };
}}>Firstname</th
>
<th
on:click={() => {
sortBy = { key: "PlayerLastname", asc: !sortBy.asc };
}}>Lastname</th
>
<th
on:click={() => {
sortBy = { key: "PlayerClub", asc: !sortBy.asc };
}}>Club</th
>
</tr>
</thead>
<tbody>
{#each filteredPlayers as player}
{#if player != null}
<tr>
<td
on:dblclick={async () => {
let newRank = await swal({
content: {
element: "input",
attributes: {
placeholder: "New rank",
type: "number",
},
},
buttons: {
cancel: true,
confirm: true,
},
});
if (newRank) {
player.PlayerInitialRank =
parseInt(newRank);
await Session.UpdateCompetitionPlayer(
competition.CompetitionID,
player
).then(() => {
loadPlayers();
});
}
}}>{player.PlayerInitialRank}</td
>
<td
on:dblclick={async () => {
let newFirstname = await swal({
content: {
element: "input",
attributes: {
placeholder: "New firstname",
},
},
buttons: {
cancel: true,
confirm: true,
},
});
if (newFirstname) {
player.PlayerFirstname = newFirstname;
await Session.UpdateCompetitionPlayer(
competition.CompetitionID,
player
).then(() => {
loadPlayers();
});
}
}}>{player.PlayerFirstname}</td
>
<td
on:dblclick={async () => {
let newLastname = await swal({
content: {
element: "input",
attributes: {
placeholder: "New lastname",
},
},
buttons: {
cancel: true,
confirm: true,
},
});
if (newLastname) {
player.PlayerLastname = newLastname;
await Session.UpdateCompetitionPlayer(
competition.CompetitionID,
player
).then(() => {
loadPlayers();
});
}
}}>{player.PlayerLastname}</td
>
<td
>{#if player.PlayerClub}{player.PlayerClub}{:else}Sans
Nom{/if}</td
>
</tr>
{/if}
{/each}
<tr id="add-player-tr">
<td colspan="4">
<button
on:click={async () => {
var player = Models.Player.createFrom({
PlayerID: 65535,
PlayerFirstname: "Firstname",
PlayerLastname: "Lastname",
PlayerNationID: 0,
PlayerClubID: 0,
PlayerRegionID: 0,
PlayerInitialRank: 2,
});
await Session.AddPlayerToCompetition(
competition.CompetitionID,
player
).then(() => {
loadPlayers();
});
}}
>
Add Player
</button></td
>
</tr>
</tbody>
</table>
</div>
<style>
.registration-container {
margin-top: 5vh;
display: flex;
flex-direction: column;
align-items: center;
}
input {
width: 200px;
margin-bottom: 10px;
padding: 10px;
font-size: 1em;
border-radius: 10px;
border: solid 1px #003566;
}
</style>
<script lang="ts"> <script lang="ts">
import { onMount } from "svelte"; import { onMount } from "svelte";
import * as Models from "../../bindings/changeme/astro/services/models"; import * as Models from "../../../bindings/changeme/astro/services/models";
import * as Session from "../../bindings/changeme/astro/services/session"; import * as Session from "../../../bindings/changeme/astro/services/session";
import swal from "sweetalert"; import swal from "sweetalert";
export let competition: Models.Competition; export let competition: Models.Competition;
......
<script lang="ts">
import { onMount } from "svelte";
import * as Models from "../../../bindings/changeme/astro/services/models";
import * as Session from "../../../bindings/changeme/astro/services/session";
import { SelectedCompetition } from "../../store";
import swal from "sweetalert";
let players: (Models.Player | null)[] = [];
let filteredPlayers: (Models.Player | null)[] = [];
let competition: Models.Competition | undefined;
SelectedCompetition.subscribe((value) => {
competition = value;
loadPlayers();
});
async function loadPlayers() {
if (competition === undefined) {
return;
}
Session.GetAllPlayersFromCompetition(competition.CompetitionID).then(
(result) => {
players = result;
}
);
}
onMount(async () => {
await loadPlayers();
});
function getPlayerValueByKey(player: Models.Player | null, key: string) {
if (player === null) {
return "";
}
switch (key) {
case "PlayerInitialRank":
return player.PlayerInitialRank;
case "PlayerFirstname":
return player.PlayerFirstname;
case "PlayerLastname":
return player.PlayerLastname;
case "PlayerClub":
return player.PlayerClub;
default:
return "";
}
}
let sortBy = { key: "PlayerInitialRank", asc: true };
$: players = players.sort((a, b) => {
let aValue = getPlayerValueByKey(a, sortBy.key);
let bValue = getPlayerValueByKey(b, sortBy.key);
if (aValue === null || bValue === null) {
return 0;
}
if (aValue < bValue) {
return sortBy.asc ? -1 : 1;
}
if (aValue > bValue) {
return sortBy.asc ? 1 : -1;
}
return 0;
});
let searchTerms = "";
$: filteredPlayers = players.filter((player) => {
if (player === null) {
return [];
}
return (
player.PlayerFirstname.toLowerCase().includes(
searchTerms.toLowerCase()
) ||
player.PlayerLastname.toLowerCase().includes(
searchTerms.toLowerCase()
) ||
player.PlayerClub?.club_name
.toLowerCase()
.includes(searchTerms.toLowerCase())
);
});
</script>
<div class="registration-container">
<input
type="text"
bind:value={searchTerms}
placeholder="Search for a player"
/>
{#if competition == undefined}
<p>No competition selected</p>
{:else}
<table>
<thead>
<tr>
<th
on:click={() => {
sortBy = {
key: "PlayerInitialRank",
asc: !sortBy.asc,
};
}}>Initial Rank</th
>
<th
on:click={() => {
sortBy = {
key: "PlayerFirstname",
asc: !sortBy.asc,
};
}}>Firstname</th
>
<th
on:click={() => {
sortBy = {
key: "PlayerLastname",
asc: !sortBy.asc,
};
}}>Lastname</th
>
<th
on:click={() => {
sortBy = { key: "PlayerClub", asc: !sortBy.asc };
}}>Club</th
>
</tr>
</thead>
<tbody>
{#each filteredPlayers as player}
{#if player != null}
<tr>
<td
on:dblclick={async () => {
let newRank = await swal({
content: {
element: "input",
attributes: {
placeholder: "New rank",
type: "number",
},
},
buttons: {
cancel: true,
confirm: true,
},
});
if (newRank) {
player.PlayerInitialRank =
parseInt(newRank);
if (isNaN(player.PlayerInitialRank)) {
await swal(
"Error",
"Rank must be a number",
"error"
);
return;
}
if (competition != undefined)
await Session.UpdateCompetitionPlayer(
competition.CompetitionID,
player
).then(() => {
loadPlayers();
});
}
}}>{player.PlayerInitialRank}</td
>
<td
on:dblclick={async () => {
let newFirstname = await swal({
content: {
element: "input",
attributes: {
placeholder: "New firstname",
},
},
buttons: {
cancel: true,
confirm: true,
},
});
if (newFirstname) {
player.PlayerFirstname = newFirstname;
if (competition != undefined)
await Session.UpdateCompetitionPlayer(
competition.CompetitionID,
player
).then(() => {
loadPlayers();
});
}
}}>{player.PlayerFirstname}</td
>
<td
on:dblclick={async () => {
let newLastname = await swal({
content: {
element: "input",
attributes: {
placeholder: "New lastname",
},
},
buttons: {
cancel: true,
confirm: true,
},
});
if (newLastname) {
player.PlayerLastname = newLastname;
if (competition != undefined)
await Session.UpdateCompetitionPlayer(
competition.CompetitionID,
player
).then(() => {
loadPlayers();
});
}
}}>{player.PlayerLastname}</td
>
<td
>{#if player.PlayerClub}{player.PlayerClub}{:else}Sans
Nom{/if}</td
>
</tr>
{/if}
{/each}
<tr id="add-player-tr">
<td colspan="4">
<button
on:click={async () => {
var player = Models.Player.createFrom({
PlayerID: 65535,
PlayerFirstname: "Firstname",
PlayerLastname: "Lastname",
PlayerNationID: 0,
PlayerClubID: 0,
PlayerRegionID: 0,
PlayerInitialRank: 2,
});
if (competition != undefined)
await Session.AddPlayerToCompetition(
competition.CompetitionID,
player
).then(() => {
loadPlayers();
});
}}
>
Add Player
</button></td
>
</tr>
</tbody>
</table>
{/if}
</div>
<style>
.registration-container {
margin-top: 5vh;
display: flex;
flex-direction: column;
align-items: center;
}
input {
width: 200px;
margin-bottom: 10px;
padding: 10px;
font-size: 1em;
border-radius: 10px;
border: solid 1px #003566;
}
</style>
...@@ -4,4 +4,4 @@ const app = new App({ ...@@ -4,4 +4,4 @@ const app = new App({
target: document.getElementById('app')!, target: document.getElementById('app')!,
}) })
export default app export default app;
\ No newline at end of file
import { writable } from 'svelte/store';
import type { Competition } from '../bindings/changeme/astro/services/models';
export const SelectedCompetition = writable<Competition | undefined>(undefined);
\ No newline at end of file
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment