Commit 69b4f458 authored by Chunchi Che's avatar Chunchi Che

handle overlay logic in service

parent 3459e7b8
Pipeline #20048 passed with stages
in 3 minutes and 24 seconds
......@@ -29,6 +29,7 @@ export interface CardState {
zone: ygopro.CardZone;
sequence: number;
}>; // 选择位置状态下的互动信息
overlay_materials?: CardMeta[]; // 超量素材
}
export enum InteractType {
......@@ -212,6 +213,18 @@ export function removeOccupant<T extends DuelFieldState>(
}
}
export function removeOverlay<T extends DuelFieldState>(
state: T | undefined,
sequence: number
) {
if (state) {
const target = state.inner.find((_, idx) => idx == sequence);
if (target) {
target.overlay_materials = [];
}
}
}
export function insertCard<T extends DuelFieldState>(
state: T | undefined,
sequence: number,
......
......@@ -3,6 +3,7 @@ import {
PayloadAction,
CaseReducer,
ActionReducerMapBuilder,
createAsyncThunk,
} from "@reduxjs/toolkit";
import { DuelState } from "./mod";
import { ygopro } from "../../api/ocgcore/idl/ocgcore";
......@@ -18,7 +19,9 @@ import {
extendIdleInteractivities,
clearIdleInteractivities,
setPosition,
removeOverlay,
} from "./generic";
import { fetchCard } from "../../api/cards";
export interface MonsterState extends DuelFieldState {}
......@@ -159,6 +162,33 @@ export const clearMonsterIdleInteractivitiesImpl: CaseReducer<
// 增加怪兽
export const fetchMonsterMeta = createAsyncMetaThunk("duel/fetchMonsterMeta");
// 增加怪兽的超量素材
export const fetchOverlayMeta = createAsyncThunk(
"duel/fetchOverlayMeta",
async (param: {
controler: number;
sequence: number;
overlayCodes: number[];
}) => {
const controler = param.controler;
const sequence = param.sequence;
const overlayCodes = param.overlayCodes;
const metas = await Promise.all(
overlayCodes.map(async (id) => {
if (id == 0) {
return { id, data: {}, text: {} };
} else {
return await fetchCard(id, true);
}
})
);
const response = { controler, sequence, metas };
return response;
}
);
export const monsterCase = (builder: ActionReducerMapBuilder<DuelState>) => {
builder.addCase(fetchMonsterMeta.pending, (state, action) => {
// Meta结果没返回之前先更新`ID`
......@@ -185,6 +215,41 @@ export const monsterCase = (builder: ActionReducerMapBuilder<DuelState>) => {
extendOccupant(state.opMonsters, meta, sequence);
}
});
builder.addCase(fetchOverlayMeta.pending, (state, action) => {
// Meta结果没返回之前先更新`ID`
const controler = action.meta.arg.controler;
const sequence = action.meta.arg.sequence;
const overlayCodes = action.meta.arg.overlayCodes;
const metas = overlayCodes.map((id) => {
return { id, data: {}, text: {} };
});
const monsters = judgeSelf(controler, state)
? state.meMonsters
: state.opMonsters;
if (monsters) {
const target = monsters.inner.find((_, idx) => idx == sequence);
if (target && target.occupant) {
target.overlay_materials = metas;
}
}
});
builder.addCase(fetchOverlayMeta.fulfilled, (state, action) => {
const controler = action.payload.controler;
const sequence = action.payload.sequence;
const overlayMetas = action.payload.metas;
const monsters = judgeSelf(controler, state)
? state.meMonsters
: state.opMonsters;
if (monsters) {
const target = monsters.inner.find((_, idx) => idx == sequence);
if (target && target.occupant) {
target.overlay_materials = overlayMetas;
}
}
});
};
// 删除怪兽
......@@ -199,6 +264,7 @@ export const removeMonsterImpl: CaseReducer<
: state.opMonsters;
removeOccupant(monsters, action.payload.sequence);
removeOverlay(monsters, action.payload.sequence);
};
// 改变怪兽表示形式
......
import { ygopro } from "../../api/ocgcore/idl/ocgcore";
import MsgMove = ygopro.StocGameMessage.MsgMove;
import { AppDispatch } from "../../store";
import { fetchMonsterMeta } from "../../reducers/duel/monstersSlice";
import {
fetchMonsterMeta,
fetchOverlayMeta,
} from "../../reducers/duel/monstersSlice";
import {
removeCemetery,
removeExclusion,
......@@ -16,11 +19,12 @@ import { insertHandMeta } from "../../reducers/duel/handsSlice";
import { fetchExclusionMeta } from "../../reducers/duel/exclusionSlice";
import { fetchExtraDeckMeta } from "../../reducers/duel/extraDeckSlice";
const OVERLAY_STACK: { code: number; sequence: number }[] = [];
export default (move: MsgMove, dispatch: AppDispatch) => {
const code = move.code;
const from = move.from;
const to = move.to;
console.log(to);
// TODO: reason
switch (from.location) {
......@@ -81,6 +85,19 @@ export default (move: MsgMove, dispatch: AppDispatch) => {
})
);
// 处理超量素材
const overlayMetarials = OVERLAY_STACK.splice(0, OVERLAY_STACK.length);
let sorted = overlayMetarials
.sort((a, b) => a.sequence - b.sequence)
.map((overlay) => overlay.code);
dispatch(
fetchOverlayMeta({
controler: to.controler,
sequence: to.sequence,
overlayCodes: sorted,
})
);
break;
}
case ygopro.CardZone.SZONE: {
......@@ -135,6 +152,11 @@ export default (move: MsgMove, dispatch: AppDispatch) => {
break;
}
case ygopro.CardZone.OVERLAY: {
OVERLAY_STACK.push({ code, sequence: to.overlay_sequence });
break;
}
default: {
console.log(`Unhandled zone type ${to.location}`);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment