3 Commits

Author SHA1 Message Date
a2576b044c feat: implement dynamic sort parameter for AniList watchlist
Add configurable sort functionality to AniList watchlist system:

- Add aniListSort writable store to GlobalVariablesAndHelperFunctions
- Update Pagination component to subscribe to and use dynamic sort parameter
- Refactor CheckIfAniListLoggedInAndLoadWatchList to use sort from store
- Remove hardcoded MediaListSort.UpdatedTimeDesc in favor of configurable sort
- Improve code formatting with arrow functions and consistent spacing
- Add sort parameter to all GetAniListUserWatchingList calls

This allows users to customize their watchlist sorting preference instead of being limited to the default 'updated time descending' sort order.
2026-03-29 10:23:58 -04:00
2ee2d85e9e feat: add Sort component placeholder
Add new Sort component to infrastructure for future sort functionality implementation in the watchlist UI.
2026-03-29 10:23:55 -04:00
1090f112f3 refactor: standardize code formatting in AvatarMenu component
- Convert from 4-space to 2-space indentation for consistency
- Improve import statement formatting and alignment
- Fix semicolon usage throughout the component
- Add conditional avatar dot indicator: green when all services (AniList, MAL, Simkl) are logged in, yellow otherwise
- Add missing newline at end of file
- General code style improvements for better readability and consistency with project standards
2026-03-22 22:00:48 -04:00
5 changed files with 222 additions and 201 deletions

View File

@@ -13,7 +13,7 @@
loginToSimkl, loginToSimkl,
logoutOfAniList, logoutOfAniList,
logoutOfMAL, logoutOfMAL,
logoutOfSimkl logoutOfSimkl,
} from "../helperModules/GlobalVariablesAndHelperFunctions.svelte"; } from "../helperModules/GlobalVariablesAndHelperFunctions.svelte";
import * as runtime from "../../wailsjs/runtime"; import * as runtime from "../../wailsjs/runtime";
import type { MyAnimeListUser } from "../mal/types/MALTypes"; import type { MyAnimeListUser } from "../mal/types/MALTypes";
@@ -28,8 +28,8 @@
let isMALLoggedIn: boolean; let isMALLoggedIn: boolean;
aniListUser.subscribe((value) => (currentAniListUser = value)); aniListUser.subscribe((value) => (currentAniListUser = value));
malUser.subscribe((value) => (currentMALUser = value)) malUser.subscribe((value) => (currentMALUser = value));
simklUser.subscribe(value => currentSimklUser = value) simklUser.subscribe((value) => (currentSimklUser = value));
aniListLoggedIn.subscribe((value) => (isAniListLoggedIn = value)); aniListLoggedIn.subscribe((value) => (isAniListLoggedIn = value));
simklLoggedIn.subscribe((value) => (isSimklLoggedIn = value)); simklLoggedIn.subscribe((value) => (isSimklLoggedIn = value));
malLoggedIn.subscribe((value) => (isMALLoggedIn = value)); malLoggedIn.subscribe((value) => (isMALLoggedIn = value));
@@ -39,17 +39,20 @@
dropdown.classList.toggle("hidden"); dropdown.classList.toggle("hidden");
if (!dropdown.classList.contains("hidden")) { if (!dropdown.classList.contains("hidden")) {
document.addEventListener("click", clickOutside) document.addEventListener("click", clickOutside);
} }
} }
function clickOutside(event: Event): void { function clickOutside(event: Event): void {
let dropdown = document.querySelector("#userDropdown") let dropdown = document.querySelector("#userDropdown");
let toggleBtn = document.querySelector("#userDropdownButton") let toggleBtn = document.querySelector("#userDropdownButton");
if (!dropdown.contains(event.target as Node) && !toggleBtn.contains(event.target as Node)) { if (
dropdown.classList.add("hidden") !dropdown.contains(event.target as Node) &&
document.removeEventListener("click", clickOutside) !toggleBtn.contains(event.target as Node)
) {
dropdown.classList.add("hidden");
document.removeEventListener("click", clickOutside);
} }
} }
</script> </script>
@@ -60,7 +63,9 @@
<Avatar <Avatar
src={currentAniListUser.data.Viewer.avatar.medium} src={currentAniListUser.data.Viewer.avatar.medium}
class="cursor-pointer" class="cursor-pointer"
dot={{ color: "green" }} dot={isAniListLoggedIn && isMALLoggedIn && isSimklLoggedIn
? { color: "green" }
: { color: "yellow" }}
/> />
{:else} {:else}
<Avatar class="cursor-pointer" dot={{ color: "red" }} /> <Avatar class="cursor-pointer" dot={{ color: "red" }} />
@@ -87,16 +92,19 @@
on:click={logoutOfAniList} on:click={logoutOfAniList}
class="block px-4 py-2 w-full hover:bg-gray-600 truncate bg-green-800 hover:text-white" class="block px-4 py-2 w-full hover:bg-gray-600 truncate bg-green-800 hover:text-white"
> >
<span class="maple-font text-lg text-green-200 mr-4">A</span>Logout {currentAniListUser.data.Viewer.name} <span class="maple-font text-lg text-green-200 mr-4">A</span>Logout {currentAniListUser
.data.Viewer.name}
</button> </button>
</li> </li>
{:else} {:else}
<li> <li>
<button on:click={() => { <button
dropdownUser() on:click={() => {
loginToAniList() dropdownUser();
loginToAniList();
}} }}
class="block px-4 py-2 w-full hover:bg-gray-600 truncate hover:text-white"> class="block px-4 py-2 w-full hover:bg-gray-600 truncate hover:text-white"
>
<span class="maple-font text-lg mr-4">A</span>Login to AniList <span class="maple-font text-lg mr-4">A</span>Login to AniList
</button> </button>
</li> </li>
@@ -112,11 +120,13 @@
</li> </li>
{:else} {:else}
<li> <li>
<button on:click={() => { <button
dropdownUser() on:click={() => {
loginToMAL() dropdownUser();
loginToMAL();
}} }}
class="block px-4 py-2 w-full hover:bg-gray-600 truncate hover:text-white"> class="block px-4 py-2 w-full hover:bg-gray-600 truncate hover:text-white"
>
<span class="maple-font text-lg mr-4">M</span>Login to MyAnimeList <span class="maple-font text-lg mr-4">M</span>Login to MyAnimeList
</button> </button>
</li> </li>
@@ -127,16 +137,19 @@
on:click={logoutOfSimkl} on:click={logoutOfSimkl}
class="block px-4 py-2 w-full hover:bg-gray-600 truncate bg-indigo-800 hover:text-white" class="block px-4 py-2 w-full hover:bg-gray-600 truncate bg-indigo-800 hover:text-white"
> >
<span class="maple-font text-lg text-indigo-200 mr-4">S</span>Logout {currentSimklUser.user.name} <span class="maple-font text-lg text-indigo-200 mr-4">S</span>Logout {currentSimklUser
.user.name}
</button> </button>
</li> </li>
{:else} {:else}
<li> <li>
<button on:click={() => { <button
dropdownUser() on:click={() => {
loginToSimkl() dropdownUser();
loginToSimkl();
}} }}
class="block px-4 py-2 w-full hover:bg-gray-600 truncate hover:text-white"> class="block px-4 py-2 w-full hover:bg-gray-600 truncate hover:text-white"
>
<span class="maple-font text-lg mr-4">S</span>Login to Simkl <span class="maple-font text-lg mr-4">S</span>Login to Simkl
</button> </button>
</li> </li>
@@ -145,8 +158,8 @@
<div class="py-2"> <div class="py-2">
<button <button
on:click={() => { on:click={() => {
dropdownUser() dropdownUser();
ShowVersion() ShowVersion();
}} }}
class="block px-4 py-2 w-full text-sm hover:bg-gray-600 text-gray-200 over:text-white" class="block px-4 py-2 w-full text-sm hover:bg-gray-600 text-gray-200 over:text-white"
> >
@@ -161,3 +174,4 @@
</div> </div>
</div> </div>
</div> </div>

View File

@@ -1,6 +1,7 @@
<script lang="ts"> <script lang="ts">
import { import {
aniListLoggedIn, aniListLoggedIn,
aniListSort,
aniListWatchlist, aniListWatchlist,
animePerPage, animePerPage,
watchListPage, watchListPage,
@@ -8,24 +9,21 @@
import type { AniListCurrentUserWatchList } from "../anilist/types/AniListCurrentUserWatchListType"; import type { AniListCurrentUserWatchList } from "../anilist/types/AniListCurrentUserWatchListType";
import { GetAniListUserWatchingList } from "../../wailsjs/go/main/App"; import { GetAniListUserWatchingList } from "../../wailsjs/go/main/App";
import { MediaListSort } from "../anilist/types/AniListTypes";
let aniListWatchListLoaded: AniListCurrentUserWatchList; let aniListWatchListLoaded: AniListCurrentUserWatchList;
let page: number; let page: number;
let perPage: number; let perPage: number;
let sort: string;
watchListPage.subscribe((value) => (page = value)); watchListPage.subscribe((value) => (page = value));
animePerPage.subscribe((value) => (perPage = value)); animePerPage.subscribe((value) => (perPage = value));
aniListWatchlist.subscribe((value) => (aniListWatchListLoaded = value)); aniListWatchlist.subscribe((value) => (aniListWatchListLoaded = value));
aniListSort.subscribe((value) => (sort = value));
const perPageOptions = [10, 20, 50]; const perPageOptions = [10, 20, 50];
function ChangeWatchListPage(newPage: number) { function ChangeWatchListPage(newPage: number) {
GetAniListUserWatchingList( GetAniListUserWatchingList(newPage, perPage, sort).then((result) => {
newPage,
perPage,
MediaListSort.UpdatedTimeDesc,
).then((result) => {
watchListPage.set(newPage); watchListPage.set(newPage);
aniListWatchlist.set(result); aniListWatchlist.set(result);
aniListLoggedIn.set(true); aniListLoggedIn.set(true);
@@ -45,16 +43,14 @@
function changeCountPerPage( function changeCountPerPage(
e: Event & { currentTarget: HTMLSelectElement }, e: Event & { currentTarget: HTMLSelectElement },
): void { ): void {
GetAniListUserWatchingList( GetAniListUserWatchingList(1, Number(e.currentTarget.value), sort).then(
1, (result) => {
Number(e.currentTarget.value),
MediaListSort.UpdatedTimeDesc,
).then((result) => {
animePerPage.set(Number(e.currentTarget.value)); animePerPage.set(Number(e.currentTarget.value));
watchListPage.set(1); watchListPage.set(1);
aniListWatchlist.set(result); aniListWatchlist.set(result);
aniListLoggedIn.set(true); aniListLoggedIn.set(true);
}); },
);
} }
</script> </script>

View File

@@ -1,34 +1,47 @@
<script lang="ts" context="module"> <script lang="ts" context="module">
import {CheckIfAniListLoggedIn, GetAniListLoggedInUser, GetAniListUserWatchingList} from "../../wailsjs/go/main/App"; import {
import {MediaListSort} from "../anilist/types/AniListTypes"; CheckIfAniListLoggedIn,
import { aniListUser, watchListPage, animePerPage, aniListPrimary, aniListLoggedIn, aniListWatchlist } from "./GlobalVariablesAndHelperFunctions.svelte" GetAniListLoggedInUser,
GetAniListUserWatchingList,
} from "../../wailsjs/go/main/App";
import {
aniListUser,
watchListPage,
animePerPage,
aniListPrimary,
aniListLoggedIn,
aniListWatchlist,
aniListSort,
} from "./GlobalVariablesAndHelperFunctions.svelte";
let isAniListPrimary: boolean let isAniListPrimary: boolean;
let page: number let page: number;
let perPage: number let perPage: number;
let sort: string;
aniListPrimary.subscribe(value => isAniListPrimary = value) aniListPrimary.subscribe((value) => (isAniListPrimary = value));
watchListPage.subscribe(value => page = value) watchListPage.subscribe((value) => (page = value));
animePerPage.subscribe(value => perPage = value) animePerPage.subscribe((value) => (perPage = value));
aniListSort.subscribe((value) => (sort = value));
export const LoadAniListUser = async () => { export const LoadAniListUser = async () => {
await GetAniListLoggedInUser().then(user => { await GetAniListLoggedInUser().then((user) => {
aniListUser.set(user) aniListUser.set(user);
}) });
} };
export const LoadAniListWatchList = async () => { export const LoadAniListWatchList = async () => {
await GetAniListUserWatchingList(page, perPage, MediaListSort.UpdatedTimeDesc).then((watchList) => { await GetAniListUserWatchingList(page, perPage, sort).then((watchList) => {
aniListWatchlist.set(watchList) aniListWatchlist.set(watchList);
}) });
} };
export const CheckIfAniListLoggedInAndLoadWatchList = async () => { export const CheckIfAniListLoggedInAndLoadWatchList = async () => {
const loggedIn = await CheckIfAniListLoggedIn() const loggedIn = await CheckIfAniListLoggedIn();
if (loggedIn) { if (loggedIn) {
await LoadAniListUser() await LoadAniListUser();
if (isAniListPrimary) await LoadAniListWatchList() if (isAniListPrimary) await LoadAniListWatchList();
}
aniListLoggedIn.set(loggedIn)
} }
aniListLoggedIn.set(loggedIn);
};
</script> </script>

View File

@@ -53,6 +53,7 @@
export let loading = writable(false); export let loading = writable(false);
export let tableItems = writable([] as TableItems); export let tableItems = writable([] as TableItems);
export let watchlistNeedsRefresh = writable(false); export let watchlistNeedsRefresh = writable(false);
export let aniListSort = writable(MediaListSort.UpdatedTimeDesc);
export let watchListPage = writable(1); export let watchListPage = writable(1);
export let animePerPage = writable(20); export let animePerPage = writable(20);
@@ -60,6 +61,7 @@
let isAniListPrimary: boolean; let isAniListPrimary: boolean;
let page: number; let page: number;
let perPage: number; let perPage: number;
let sort: string;
let aniWatchlist: AniListCurrentUserWatchList; let aniWatchlist: AniListCurrentUserWatchList;
let currentAniListAnime: AniListGetSingleAnime; let currentAniListAnime: AniListGetSingleAnime;
@@ -73,6 +75,7 @@
malLoggedIn.subscribe((value) => (isMalLoggedIn = value)); malLoggedIn.subscribe((value) => (isMalLoggedIn = value));
simklLoggedIn.subscribe((value) => (isSimklLoggedIn = value)); simklLoggedIn.subscribe((value) => (isSimklLoggedIn = value));
aniListAnime.subscribe((value) => (currentAniListAnime = value)); aniListAnime.subscribe((value) => (currentAniListAnime = value));
aniListSort.subscribe((value) => (sort = value));
export async function GetAnimeSingleItem( export async function GetAnimeSingleItem(
aniId: number, aniId: number,
@@ -136,11 +139,7 @@
GetAniListLoggedInUser().then((result) => { GetAniListLoggedInUser().then((result) => {
aniListUser.set(result); aniListUser.set(result);
if (isAniListPrimary) { if (isAniListPrimary) {
GetAniListUserWatchingList( GetAniListUserWatchingList(page, perPage, sort).then((result) => {
page,
perPage,
MediaListSort.UpdatedTimeDesc,
).then((result) => {
aniListWatchlist.set(result); aniListWatchlist.set(result);
aniListLoggedIn.set(true); aniListLoggedIn.set(true);
}); });
@@ -184,4 +183,3 @@
}); });
} }
</script> </script>