Skip to content

Commit bc696f8

Browse files
PoC of mod download/install through vuex store
TODO: Installation is not yet done, but it should be pretty similar to download.
1 parent 5e73a77 commit bc696f8

File tree

3 files changed

+125
-43
lines changed

3 files changed

+125
-43
lines changed

src/components/views/DownloadModModal.vue

Lines changed: 26 additions & 43 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,14 @@
11
<template>
22
<div>
3-
<div id='downloadProgressModal' :class="['modal', {'is-active':downloadingMod}]" v-if="downloadObject !== null">
3+
<div id='downloadProgressModal' :class="['modal', {'is-active':downloadingMod}]" v-if="downloadingMod">
44
<div class="modal-background" @click="downloadingMod = false;"></div>
55
<div class='modal-content'>
66
<div class='notification is-info'>
7-
<h3 class='title'>Downloading {{downloadObject.modName}}</h3>
8-
<p>{{Math.floor(downloadObject.progress)}}% complete</p>
7+
<h3 class='title'>Downloading {{activeDownloadModName}}</h3>
8+
<p>{{Math.floor(downloadProgress)}}% complete</p>
99
<Progress
1010
:max='100'
11-
:value='downloadObject.progress'
11+
:value='downloadProgress'
1212
:className="['is-dark']"
1313
/>
1414
</div>
@@ -91,6 +91,7 @@
9191
<script lang="ts">
9292
9393
import { Component, Vue, Watch } from 'vue-property-decorator';
94+
import { mapGetters } from 'vuex';
9495
import ThunderstoreMod from '../../model/ThunderstoreMod';
9596
import ManifestV2 from '../../model/ManifestV2';
9697
import ThunderstoreVersion from '../../model/ThunderstoreVersion';
@@ -123,6 +124,11 @@ let assignId = 0;
123124
components: {
124125
ModalCard,
125126
Progress
127+
},
128+
computed: {
129+
...mapGetters({
130+
activeDownloadProgress: 'modDownload/activeDownloadProgress'
131+
})
126132
}
127133
})
128134
export default class DownloadModModal extends Vue {
@@ -133,6 +139,8 @@ let assignId = 0;
133139
downloadingMod: boolean = false;
134140
selectedVersion: string | null = null;
135141
currentVersion: string | null = null;
142+
downloadProgress: number | null = 0;
143+
activeDownloadModName: string | null = null;
136144
137145
static allVersions: [number, DownloadProgress][] = [];
138146
@@ -220,6 +228,11 @@ let assignId = 0;
220228
return this.$store.state.modals.isDownloadModModalOpen;
221229
}
222230
231+
@Watch('activeDownloadProgress')
232+
async updateProgress() {
233+
this.downloadProgress = this.$store.getters['modDownload/activeDownloadProgress'];
234+
}
235+
223236
@Watch('$store.state.modals.downloadModModalMod')
224237
async getModVersions() {
225238
this.currentVersion = null;
@@ -326,47 +339,17 @@ let assignId = 0;
326339
}, this.downloadCompletedCallback);
327340
}
328341
329-
downloadHandler(tsMod: ThunderstoreMod, tsVersion: ThunderstoreVersion) {
342+
async downloadHandler(tsMod: ThunderstoreMod, tsVersion: ThunderstoreVersion) {
330343
this.closeModal();
331-
const currentAssignId = assignId++;
332-
const progressObject = {
333-
progress: 0,
334-
initialMods: [`${tsMod.getName()} (${tsVersion.getVersionNumber().toString()})`],
335-
modName: '',
336-
assignId: currentAssignId,
337-
failed: false,
338-
};
339-
this.downloadObject = progressObject;
340-
DownloadModModal.allVersions.push([currentAssignId, this.downloadObject]);
344+
this.activeDownloadModName = tsMod.getName();
341345
this.downloadingMod = true;
342-
setTimeout(() => {
343-
ThunderstoreDownloaderProvider.instance.download(this.profile.asImmutableProfile(), tsMod, tsVersion, this.ignoreCache, (progress: number, modName: string, status: number, err: R2Error | null) => {
344-
const assignIndex = DownloadModModal.allVersions.findIndex(([number, val]) => number === currentAssignId);
345-
if (status === StatusEnum.FAILURE) {
346-
if (err !== null) {
347-
this.downloadingMod = false;
348-
const existing = DownloadModModal.allVersions[assignIndex]
349-
existing[1].failed = true;
350-
this.$set(DownloadModModal.allVersions, assignIndex, [currentAssignId, existing[1]]);
351-
DownloadModModal.addSolutionsToError(err);
352-
this.$store.commit('error/handleError', err);
353-
return;
354-
}
355-
} else if (status === StatusEnum.PENDING) {
356-
const obj = {
357-
progress: progress,
358-
initialMods: [`${tsMod.getName()} (${tsVersion.getVersionNumber().toString()})`],
359-
modName: modName,
360-
assignId: currentAssignId,
361-
failed: false,
362-
}
363-
if (this.downloadObject!.assignId === currentAssignId) {
364-
this.downloadObject = Object.assign({}, obj);
365-
}
366-
this.$set(DownloadModModal.allVersions, assignIndex, [currentAssignId, obj]);
367-
}
368-
}, this.downloadCompletedCallback);
369-
}, 1);
346+
347+
await this.$store.dispatch(
348+
'modDownload/downloadAndInstallMod',
349+
{ profile: this.profile.asImmutableProfile(), mod: tsMod, version: tsVersion }
350+
).catch((reason) => this.$store.commit('error/handleError', R2Error.fromThrownValue(reason)));
351+
this.activeDownloadModName = null;
352+
this.downloadingMod = false;
370353
}
371354
372355
async downloadCompletedCallback(downloadedMods: ThunderstoreCombo[]) {

src/store/index.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ import GameManager from '../model/game/GameManager';
1313
import R2Error from '../model/errors/R2Error';
1414
import { getModLoaderPackageNames } from '../r2mm/installing/profile_installers/ModLoaderVariantRecord';
1515
import ManagerSettings from '../r2mm/manager/ManagerSettings';
16+
import ModDownloadModule from "../store/modules/ModDownloadModule";
1617

1718
Vue.use(Vuex);
1819

@@ -128,6 +129,7 @@ export const store = {
128129
profile: ProfileModule,
129130
profiles: ProfilesModule,
130131
tsMods: TsModsModule,
132+
modDownload: ModDownloadModule,
131133
},
132134

133135
// enable strict mode (adds overhead!)
Lines changed: 97 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,97 @@
1+
import { ActionTree, GetterTree } from 'vuex';
2+
3+
import StatusEnum from '../../model/enums/StatusEnum';
4+
import { ImmutableProfile } from '../../model/Profile';
5+
import ThunderstoreCombo from '../../model/ThunderstoreCombo';
6+
import ThunderstoreMod from '../../model/ThunderstoreMod';
7+
import ThunderstoreVersion from '../../model/ThunderstoreVersion';
8+
import ThunderstoreDownloaderProvider from '../../providers/ror2/downloading/ThunderstoreDownloaderProvider';
9+
10+
import { State as RootState } from '../index';
11+
12+
interface Progress {
13+
progress: number;
14+
status: number; // StatusEnum
15+
}
16+
17+
interface ModProgressItem {
18+
mod: ThunderstoreMod;
19+
version: ThunderstoreVersion;
20+
installProgress: Progress;
21+
downloadProgress: Progress;
22+
}
23+
24+
interface State {
25+
allDownloads: ModProgressItem[];
26+
}
27+
28+
/**
29+
* State for Mod Downloadning/Installation.
30+
*/
31+
export default {
32+
namespaced: true,
33+
34+
state: (): State => ({
35+
allDownloads: [],
36+
}),
37+
38+
getters: <GetterTree<State, RootState>>{
39+
allDownloads(state): ModProgressItem[] {
40+
return state.allDownloads;
41+
},
42+
activeDownload(state): ModProgressItem {
43+
return state.allDownloads.slice(-1)[0]; // Last element of the array
44+
},
45+
activeDownloadProgress(state): number | undefined {
46+
if(state.allDownloads.length > 0) {
47+
return state.allDownloads.slice(-1)[0].downloadProgress.progress; // Last element of the array
48+
}
49+
},
50+
},
51+
mutations: {},
52+
actions: <ActionTree<State, RootState>>{
53+
54+
//TODO: Do the installation
55+
async downloadAndInstallMod(
56+
{dispatch, getters, state},
57+
params: {
58+
profile: ImmutableProfile,
59+
mod: ThunderstoreMod,
60+
version: ThunderstoreVersion,
61+
}
62+
): Promise<boolean> {
63+
state.allDownloads.push({
64+
mod: params.mod,
65+
version: params.version,
66+
installProgress: { progress: 0, status: StatusEnum.PENDING },
67+
downloadProgress: { progress: 0, status: StatusEnum.PENDING }
68+
});
69+
70+
return new Promise((resolve, reject) => {
71+
ThunderstoreDownloaderProvider.instance.download(
72+
params.profile,
73+
params.mod,
74+
params.version,
75+
true,
76+
(progress, modName, status, err) => {
77+
const index = state.allDownloads.findIndex((modProgressItem) => modProgressItem.mod.getName() === modName);
78+
79+
if (status === StatusEnum.FAILURE) {
80+
if(err) {
81+
reject(err);
82+
}
83+
}
84+
if (status === StatusEnum.PENDING) {
85+
if (index !== -1) {
86+
state.allDownloads[index].downloadProgress = { progress: progress, status: status };
87+
}
88+
}
89+
},
90+
() => {
91+
resolve(true);
92+
}
93+
);
94+
});
95+
},
96+
},
97+
}

0 commit comments

Comments
 (0)