aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRémy Raes <contact@remyraes.com>2023-06-11 01:17:41 +0200
committerGitHub <noreply@github.com>2023-06-11 01:17:41 +0200
commit7254c28aaf5e890114ec5726ad4869fbab44d776 (patch)
tree12bc693794dbcf8f06e260495960014a4d68aced
parentf0edbfb315304dae1386bd5a10ce7fc6bd841043 (diff)
downloadFlightCore-7254c28aaf5e890114ec5726ad4869fbab44d776.tar.gz
FlightCore-7254c28aaf5e890114ec5726ad4869fbab44d776.zip
feat: Show outdated Thunderstore mods first (#385)
* feat: add isThunderstoreModOutdated method to utils * feat: display a badge on menu if there are some outdated thunderstore mods * feat: always display outdated mods first * feat: fetch Thunderstore mods on mods view mount To display the count of outdated Thunderstore mods on mods main page, we need to fetch them. * style: Update src-vue/src/components/ModsMenu.vue * style: Update src-vue/src/utils/thunderstore/version.ts * style: Update src-vue/src/views/mods/ThunderstoreModsView.vue * docs: improve outdated mods comment * docs: add comment regarding versions ordering
-rw-r--r--src-vue/src/components/ModsMenu.vue25
-rw-r--r--src-vue/src/utils/thunderstore/version.ts33
-rw-r--r--src-vue/src/views/ModsView.vue4
-rw-r--r--src-vue/src/views/mods/ThunderstoreModsView.vue15
4 files changed, 75 insertions, 2 deletions
diff --git a/src-vue/src/components/ModsMenu.vue b/src-vue/src/components/ModsMenu.vue
index 03eea787..66ecc71a 100644
--- a/src-vue/src/components/ModsMenu.vue
+++ b/src-vue/src/components/ModsMenu.vue
@@ -9,7 +9,15 @@
<el-icon><Folder /></el-icon>
<span>{{ $t('mods.menu.local') }}</span>
</el-menu-item>
- <el-menu-item index="2" @click="$emit('showLocalMods', false)">
+
+ <!-- Display a badge if there are some outdated Thunderstore mods -->
+ <el-menu-item v-if="outdatedThunderstoreModsCount !== 0" index="2" @click="$emit('showLocalMods', false)">
+ <el-badge :value="outdatedThunderstoreModsCount" class="item" type="warning">
+ <el-icon><Connection /></el-icon>
+ <span>{{ $t('mods.menu.online') }}</span>
+ </el-badge>
+ </el-menu-item>
+ <el-menu-item v-else index="2" @click="$emit('showLocalMods', false)">
<el-icon><Connection /></el-icon>
<span>{{ $t('mods.menu.online') }}</span>
</el-menu-item>
@@ -50,6 +58,8 @@
<script lang="ts">
import { defineComponent } from 'vue'
import { SortOptions } from '../utils/SortOptions.d';
+import { isThunderstoreModOutdated } from "../utils/thunderstore/version";
+import { ThunderstoreMod } from "../../../src-tauri/bindings/ThunderstoreMod";
export default defineComponent({
name: 'ModsMenu',
@@ -63,6 +73,11 @@ export default defineComponent({
this.$store.state.search.sortValue = this.sortValues[3].value;
},
computed: {
+ outdatedThunderstoreModsCount(): number {
+ return this.$store.state.thunderstoreMods
+ .filter((mod: ThunderstoreMod) => isThunderstoreModOutdated(mod))
+ .length;
+ },
sortValues(): { label: string, value: string }[] {
return Object.keys(SortOptions).map((key: string) => ({
value: key,
@@ -115,4 +130,12 @@ export default defineComponent({
width: 100%;
margin-top: 5px;
}
+
+/* Outdated thunderstore mods count */
+.el-badge {
+ width: 100%;
+}
+.el-badge:deep(.el-badge__content) {
+ top: 28px !important;
+}
</style>
diff --git a/src-vue/src/utils/thunderstore/version.ts b/src-vue/src/utils/thunderstore/version.ts
new file mode 100644
index 00000000..a111e08c
--- /dev/null
+++ b/src-vue/src/utils/thunderstore/version.ts
@@ -0,0 +1,33 @@
+import {ThunderstoreMod} from "../../../../src-tauri/bindings/ThunderstoreMod";
+import {NorthstarMod} from "../../../../src-tauri/bindings/NorthstarMod";
+import {store} from "../../plugins/store";
+
+/**
+ * Strips off a Thunderstore dependency string from its version
+ * (e.g. "taskinoz-WallrunningTitans-1.0.0" to
+ * "taskinoz-WallrunningTitans").
+ **/
+function getThunderstoreDependencyStringPrefix(dependency: string): string {
+ const dependencyStringMembers = dependency.split('-');
+ return `${dependencyStringMembers[0]}-${dependencyStringMembers[1]}`;
+}
+
+function isThunderstoreModOutdated(mod: ThunderstoreMod): boolean {
+ // Ensure mod is up-to-date.
+ const tsModPrefix = getThunderstoreDependencyStringPrefix(mod.versions[0].full_name);
+ const matchingMods: NorthstarMod[] = store.state.installed_mods.filter((mod: NorthstarMod) => {
+ if (!mod.thunderstore_mod_string) return false;
+ return getThunderstoreDependencyStringPrefix(mod.thunderstore_mod_string!) === tsModPrefix;
+ });
+ if (matchingMods.length !== 0) {
+ // There shouldn't be several mods with same dependency string, but we never know...
+ const matchingMod = matchingMods[0];
+ // A mod is outdated if its dependency strings differs from Thunderstore dependency string
+ // (no need for semver check here).
+ // This assumes mod versions list is sorted from newest to oldest version.
+ return matchingMod.thunderstore_mod_string !== mod.versions[0].full_name;
+ }
+ return false;
+}
+
+export { isThunderstoreModOutdated };
diff --git a/src-vue/src/views/ModsView.vue b/src-vue/src/views/ModsView.vue
index 7c309832..a821dcda 100644
--- a/src-vue/src/views/ModsView.vue
+++ b/src-vue/src/views/ModsView.vue
@@ -37,6 +37,10 @@ export default defineComponent({
return {
show_local_mods: true,
}
+ },
+ mounted() {
+ // Fetch Thunderstore mods to eventually display outdated mods count
+ this.$store.commit('fetchThunderstoreMods');
}
});
</script>
diff --git a/src-vue/src/views/mods/ThunderstoreModsView.vue b/src-vue/src/views/mods/ThunderstoreModsView.vue
index 538a895f..6f5e8acf 100644
--- a/src-vue/src/views/mods/ThunderstoreModsView.vue
+++ b/src-vue/src/views/mods/ThunderstoreModsView.vue
@@ -52,6 +52,8 @@ import { ElScrollbar, ScrollbarInstance } from "element-plus";
import { SortOptions } from "../../utils/SortOptions.d";
import { ThunderstoreModVersion } from "../../../../src-tauri/bindings/ThunderstoreModVersion";
import { fuzzy_filter } from "../../utils/filter";
+import { isThunderstoreModOutdated } from "../../utils/thunderstore/version";
+
export default defineComponent({
name: "ThunderstoreModsView",
@@ -137,7 +139,18 @@ export default defineComponent({
throw new Error('Unknown mod sorting.');
}
- return mods.sort(compare);
+ // Always display outdated mods first
+ // (regardless of actual sort order)
+ const sortedMods = mods.sort(compare);
+ return sortedMods.sort((a, b) => {
+ if (isThunderstoreModOutdated(a)) {
+ return -1;
+ } else if (isThunderstoreModOutdated(b)) {
+ return 1;
+ } else {
+ return compare(a, b);
+ }
+ })
},
modsPerPage(): number {
return parseInt(this.$store.state.mods_per_page);