Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Sign in / Register
Toggle navigation
N
Neos
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Locked Files
Issues
0
Issues
0
List
Boards
Labels
Service Desk
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Security & Compliance
Security & Compliance
Dependency List
License Compliance
Packages
Packages
List
Container Registry
Analytics
Analytics
CI / CD
Code Review
Insights
Issues
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
love_飞影
Neos
Commits
fdecfd97
Commit
fdecfd97
authored
Apr 18, 2023
by
timel
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
feat: valtio store logic 30%
parent
ab716aa8
Changes
6
Hide whitespace changes
Inline
Side-by-side
Showing
6 changed files
with
180 additions
and
53 deletions
+180
-53
src/api/cards.ts
src/api/cards.ts
+3
-0
src/service/duel/draw.ts
src/service/duel/draw.ts
+6
-0
src/service/duel/move.ts
src/service/duel/move.ts
+6
-1
src/service/duel/start.ts
src/service/duel/start.ts
+17
-0
src/valtioStores/duelStore/playMat.ts
src/valtioStores/duelStore/playMat.ts
+110
-27
src/valtioStores/duelStore/types.ts
src/valtioStores/duelStore/types.ts
+38
-25
No files found.
src/api/cards.ts
View file @
fdecfd97
...
@@ -66,6 +66,9 @@ export async function fetchCard(
...
@@ -66,6 +66,9 @@ export async function fetchCard(
return
res
.
data
;
return
res
.
data
;
}
}
// 挂到全局 以便 debug
window
.
fetchCard
=
fetchCard
;
export
function
getCardStr
(
meta
:
CardMeta
,
idx
:
number
):
string
|
undefined
{
export
function
getCardStr
(
meta
:
CardMeta
,
idx
:
number
):
string
|
undefined
{
switch
(
idx
)
{
switch
(
idx
)
{
case
0
:
{
case
0
:
{
...
...
src/service/duel/draw.ts
View file @
fdecfd97
...
@@ -3,10 +3,16 @@ import { fetchHandsMeta } from "@/reducers/duel/handsSlice";
...
@@ -3,10 +3,16 @@ import { fetchHandsMeta } from "@/reducers/duel/handsSlice";
import
{
fetchEsHintMeta
}
from
"
@/reducers/duel/hintSlice
"
;
import
{
fetchEsHintMeta
}
from
"
@/reducers/duel/hintSlice
"
;
import
{
AppDispatch
}
from
"
@/store
"
;
import
{
AppDispatch
}
from
"
@/store
"
;
import
{
valtioStore
}
from
"
@/valtioStores
"
;
export
default
(
export
default
(
draw
:
ygopro
.
StocGameMessage
.
MsgDraw
,
draw
:
ygopro
.
StocGameMessage
.
MsgDraw
,
dispatch
:
AppDispatch
dispatch
:
AppDispatch
)
=>
{
)
=>
{
dispatch
(
fetchEsHintMeta
({
originMsg
:
"
玩家抽卡时
"
}));
dispatch
(
fetchEsHintMeta
({
originMsg
:
"
玩家抽卡时
"
}));
dispatch
(
fetchHandsMeta
({
controler
:
draw
.
player
,
codes
:
draw
.
cards
}));
dispatch
(
fetchHandsMeta
({
controler
:
draw
.
player
,
codes
:
draw
.
cards
}));
const
playMat
=
valtioStore
.
duelStore
.
playMat
;
playMat
.
hands
.
add
(
draw
.
player
,
draw
.
cards
);
};
};
src/service/duel/move.ts
View file @
fdecfd97
...
@@ -20,8 +20,12 @@ import {
...
@@ -20,8 +20,12 @@ import {
}
from
"
@/reducers/duel/monstersSlice
"
;
}
from
"
@/reducers/duel/monstersSlice
"
;
import
{
AppDispatch
}
from
"
@/store
"
;
import
{
AppDispatch
}
from
"
@/store
"
;
import
{
valtioStore
}
from
"
@/valtioStores
"
;
import
{
REASON_MATERIAL
}
from
"
../../common
"
;
import
{
REASON_MATERIAL
}
from
"
../../common
"
;
const
{
playMat
:
playMatStore
}
=
valtioStore
.
duelStore
;
const
OVERLAY_STACK
:
{
code
:
number
;
sequence
:
number
}[]
=
[];
const
OVERLAY_STACK
:
{
code
:
number
;
sequence
:
number
}[]
=
[];
export
default
(
move
:
MsgMove
,
dispatch
:
AppDispatch
)
=>
{
export
default
(
move
:
MsgMove
,
dispatch
:
AppDispatch
)
=>
{
...
@@ -33,7 +37,7 @@ export default (move: MsgMove, dispatch: AppDispatch) => {
...
@@ -33,7 +37,7 @@ export default (move: MsgMove, dispatch: AppDispatch) => {
switch
(
from
.
location
)
{
switch
(
from
.
location
)
{
case
ygopro
.
CardZone
.
HAND
:
{
case
ygopro
.
CardZone
.
HAND
:
{
dispatch
(
removeHand
([
from
.
controler
,
from
.
sequence
]));
dispatch
(
removeHand
([
from
.
controler
,
from
.
sequence
]));
playMatStore
.
hands
.
remove
(
from
.
controler
,
from
.
sequence
);
break
;
break
;
}
}
case
ygopro
.
CardZone
.
MZONE
:
{
case
ygopro
.
CardZone
.
MZONE
:
{
...
@@ -144,6 +148,7 @@ export default (move: MsgMove, dispatch: AppDispatch) => {
...
@@ -144,6 +148,7 @@ export default (move: MsgMove, dispatch: AppDispatch) => {
dispatch
(
dispatch
(
insertHandMeta
({
controler
:
to
.
controler
,
sequence
:
to
.
sequence
,
code
})
insertHandMeta
({
controler
:
to
.
controler
,
sequence
:
to
.
sequence
,
code
})
);
);
playMatStore
.
hands
.
insert
(
to
.
controler
,
to
.
sequence
,
code
);
break
;
break
;
}
}
...
...
src/service/duel/start.ts
View file @
fdecfd97
...
@@ -11,11 +11,28 @@ import {
...
@@ -11,11 +11,28 @@ import {
}
from
"
@/reducers/duel/mod
"
;
}
from
"
@/reducers/duel/mod
"
;
import
{
AppDispatch
}
from
"
@/store
"
;
import
{
AppDispatch
}
from
"
@/store
"
;
import
{
valtioStore
}
from
"
@/valtioStores
"
;
const
playMatStore
=
valtioStore
.
duelStore
.
playMat
;
export
default
(
export
default
(
start
:
ygopro
.
StocGameMessage
.
MsgStart
,
start
:
ygopro
.
StocGameMessage
.
MsgStart
,
dispatch
:
AppDispatch
dispatch
:
AppDispatch
)
=>
{
)
=>
{
dispatch
(
setSelfType
(
start
.
playerType
));
dispatch
(
setSelfType
(
start
.
playerType
));
playMatStore
.
selfType
=
start
.
playerType
;
playMatStore
.
initInfo
.
set
(
0
,
{
life
:
start
.
life1
,
deckSize
:
start
.
deckSize1
,
extraSize
:
start
.
extraSize1
,
});
playMatStore
.
initInfo
.
set
(
1
,
{
life
:
start
.
life2
,
deckSize
:
start
.
deckSize2
,
extraSize
:
start
.
extraSize2
,
});
dispatch
(
dispatch
(
infoInit
([
infoInit
([
0
,
0
,
...
...
src/valtioStores/duelStore/playMat.ts
View file @
fdecfd97
import
{
proxy
}
from
"
valtio
"
;
import
{
proxy
}
from
"
valtio
"
;
import
{
ygopro
}
from
"
@/api/ocgcore/idl/ocgcore
"
;
import
{
ygopro
}
from
"
@/api/ocgcore/idl/ocgcore
"
;
import
{
fetchCard
}
from
"
@/api/cards
"
;
import
type
{
PlayMatState
}
from
"
./types
"
;
import
type
{
PlayMatState
,
DuelFieldState
,
CardsBothSide
,
BothSide
,
InitInfo
,
}
from
"
./types
"
;
/**
/**
* 生成一个指定长度的卡片数组
* 生成一个指定长度的卡片数组
*/
*/
function
gen
DuelFieldState
(
location
:
ygopro
.
CardZone
,
n
:
number
=
5
)
{
function
gen
Block
(
location
:
ygopro
.
CardZone
,
n
:
number
=
5
)
{
return
{
return
{
inner
:
Array
(
n
)
me
:
Array
(
n
)
.
fill
(
null
)
.
map
((
_
)
=>
({
location
:
{
location
,
},
idleInteractivities
:
[],
counters
:
{},
})),
op
:
Array
(
n
)
.
fill
(
null
)
.
fill
(
null
)
.
map
((
_
)
=>
({
.
map
((
_
)
=>
({
location
:
{
location
:
{
...
@@ -21,36 +36,86 @@ function genDuelFieldState(location: ygopro.CardZone, n: number = 5) {
...
@@ -21,36 +36,86 @@ function genDuelFieldState(location: ygopro.CardZone, n: number = 5) {
};
};
}
}
export
const
playMat
=
proxy
<
PlayMatState
>
({
const
initInfo
:
PlayMatState
[
"
initInfo
"
]
=
proxy
({
opMagics
:
genDuelFieldState
(
ygopro
.
CardZone
.
SZONE
),
me
:
{
meMagics
:
genDuelFieldState
(
ygopro
.
CardZone
.
SZONE
),
opMonsters
:
genDuelFieldState
(
ygopro
.
CardZone
.
MZONE
),
meMonsters
:
genDuelFieldState
(
ygopro
.
CardZone
.
MZONE
),
opGraveyard
:
{
inner
:
[]
},
meGraveyard
:
{
inner
:
[]
},
opBanishedZone
:
{
inner
:
[]
},
meBanishedZone
:
{
inner
:
[]
},
opHands
:
{
inner
:
[]
},
meHands
:
{
inner
:
[]
},
opDeck
:
{
inner
:
[]
},
meDeck
:
{
inner
:
[]
},
opExtraDeck
:
{
inner
:
[]
},
meExtraDeck
:
{
inner
:
[]
},
selfType
:
ygopro
.
StocTypeChange
.
SelfType
.
UNKNOWN
,
meInitInfo
:
{
masterRule
:
"
UNKNOWN
"
,
masterRule
:
"
UNKNOWN
"
,
life
:
7999
,
// 特地设置一个不可能的值
life
:
-
1
,
// 特地设置一个不可能的值
deckSize
:
0
,
deckSize
:
0
,
extraSize
:
0
,
extraSize
:
0
,
},
},
op
InitInfo
:
{
op
:
{
masterRule
:
""
,
masterRule
:
"
UNKNOWN
"
,
life
:
7999
,
// 特地设置一个不可能的值
life
:
-
1
,
// 特地设置一个不可能的值
deckSize
:
0
,
deckSize
:
0
,
extraSize
:
0
,
extraSize
:
0
,
},
},
set
:
(
controller
:
number
,
obj
:
Partial
<
InitInfo
>
)
=>
{
initInfo
[
getWhom
(
controller
)]
=
{
...
initInfo
[
getWhom
(
controller
)],
...
obj
,
};
},
});
/**
* 给 `{me: [...], op: [...]}` 这种类型的对象添加一些方法
*/
const
wrap
=
<
T
extends
DuelFieldState
>
(
entity
:
BothSide
<
T
>
,
zone
:
ygopro
.
CardZone
):
CardsBothSide
<
T
>
=>
{
/**
* 生成一个卡片,根据`id`获取卡片信息
*/
const
genCard
=
async
(
controller
:
number
,
id
:
number
)
=>
({
occupant
:
await
fetchCard
(
id
,
true
),
location
:
{
controler
:
controller
,
location
:
zone
,
},
counters
:
{},
idleInteractivities
:
[],
});
const
res
:
CardsBothSide
<
T
>
=
proxy
({
...
entity
,
remove
:
(
controller
:
number
,
sequence
:
number
)
=>
{
res
[
getWhom
(
controller
)].
splice
(
sequence
,
1
);
},
insert
:
async
(
controller
:
number
,
sequence
:
number
,
id
:
number
)
=>
{
const
card
=
await
genCard
(
controller
,
id
);
res
[
getWhom
(
controller
)].
splice
(
sequence
,
0
,
card
);
},
add
:
async
(
controller
:
number
,
ids
:
number
[])
=>
{
const
cards
=
await
Promise
.
all
(
ids
.
map
(
async
(
id
)
=>
genCard
(
controller
,
id
))
);
res
[
getWhom
(
controller
)].
splice
(
res
[
getWhom
(
controller
)].
length
,
0
,
...
cards
);
},
});
return
res
;
};
export
const
playMat
=
proxy
<
PlayMatState
>
({
magics
:
wrap
(
genBlock
(
ygopro
.
CardZone
.
SZONE
),
ygopro
.
CardZone
.
SZONE
),
monsters
:
wrap
(
genBlock
(
ygopro
.
CardZone
.
MZONE
),
ygopro
.
CardZone
.
MZONE
),
graveyard
:
wrap
({
me
:
[],
op
:
[]
},
ygopro
.
CardZone
.
GRAVE
),
banishedZone
:
wrap
({
me
:
[],
op
:
[]
},
ygopro
.
CardZone
.
REMOVED
),
hands
:
wrap
({
me
:
[],
op
:
[]
},
ygopro
.
CardZone
.
HAND
),
deck
:
wrap
({
me
:
[],
op
:
[]
},
ygopro
.
CardZone
.
DECK
),
extraDeck
:
wrap
({
me
:
[],
op
:
[]
},
ygopro
.
CardZone
.
EXTRA
),
initInfo
,
timeLimit
:
{
me
:
0
,
op
:
0
,
},
selfType
:
ygopro
.
StocTypeChange
.
SelfType
.
UNKNOWN
,
hint
:
{
hint
:
{
code
:
-
1
,
code
:
-
1
,
},
},
...
@@ -65,3 +130,21 @@ export const playMat = proxy<PlayMatState>({
...
@@ -65,3 +130,21 @@ export const playMat = proxy<PlayMatState>({
waiting
:
false
,
waiting
:
false
,
unimplemented
:
0
,
unimplemented
:
0
,
});
});
const
getWhom
=
(
controller
:
number
)
=>
judgeSelf
(
controller
,
playMat
.
selfType
)
?
"
me
"
:
"
op
"
;
export
function
judgeSelf
(
player
:
number
,
selfType
:
number
):
boolean
{
switch
(
selfType
)
{
case
1
:
// 自己是先攻
return
player
===
0
;
case
2
:
// 自己是后攻
return
player
===
1
;
default
:
// 目前不可能出现这种情况
console
.
error
(
"
judgeSelf error
"
,
player
,
selfType
);
return
false
;
}
}
src/valtioStores/duelStore/types.ts
View file @
fdecfd97
...
@@ -2,34 +2,40 @@ import type { CardMeta } from "@/api/cards";
...
@@ -2,34 +2,40 @@ import type { CardMeta } from "@/api/cards";
import
type
{
ygopro
}
from
"
@/api/ocgcore/idl/ocgcore
"
;
import
type
{
ygopro
}
from
"
@/api/ocgcore/idl/ocgcore
"
;
// >>> play mat state >>>
// >>> play mat state >>>
export
type
BothSide
<
T
>
=
{
me
:
T
;
op
:
T
;
};
export
interface
CardsBothSide
<
T
extends
DuelFieldState
>
extends
BothSide
<
T
>
{
remove
:
(
player
:
number
,
sequence
:
number
)
=>
void
;
// 移除特定位置的卡片
add
:
(
controller
:
number
,
ids
:
number
[])
=>
void
;
// 在末尾添加卡片
insert
:
(
controller
:
number
,
sequence
:
number
,
id
:
number
)
=>
void
;
// 在指定位置插入卡片
}
export
interface
PlayMatState
{
export
interface
PlayMatState
{
selfType
:
number
;
selfType
:
number
;
meInitInfo
:
InitInfo
;
// 自己的初始状态
opInitInfo
:
InitInfo
;
// 对手的初始状态
meHands
:
HandState
;
// 自己的手牌
initInfo
:
BothSide
<
InitInfo
>
&
{
opHands
:
HandState
;
// 对手的手牌
set
:
(
controller
:
number
,
obj
:
Partial
<
InitInfo
>
)
=>
void
;
};
// 双方的初始化信息
meMonsters
:
MonsterState
;
// 自己的怪兽区状态
hands
:
CardsBothSide
<
HandState
>
;
// 双方的手牌
opMonsters
:
MonsterState
;
// 对手的怪兽区状态
meMagics
:
MagicState
;
// 自己的魔法陷阱区状态
monsters
:
CardsBothSide
<
MonsterState
>
;
// 双方的怪兽区状态
opMagics
:
MagicState
;
// 对手的魔法陷阱区状态
meGraveyard
:
GraveyardState
;
// 自己的墓地状态
magics
:
CardsBothSide
<
MagicState
>
;
// 双方的魔法区状态
opGraveyard
:
GraveyardState
;
// 对手的墓地状态
meBanishedZone
:
BanishedZoneState
;
// 自己的除外区状态
graveyard
:
CardsBothSide
<
GraveyardState
>
;
// 双方的墓地状态
opBanishedZone
:
BanishedZoneState
;
// 对手的除外区状态
meDeck
:
DeckState
;
// 自己的卡组状态
banishedZone
:
CardsBothSide
<
BanishedZoneState
>
;
// 双方的除外区状态
opDeck
:
DeckState
;
// 对手的卡组状态
meExtraDeck
:
ExtraDeckState
;
// 自己的额外卡组状态
deck
:
CardsBothSide
<
DeckState
>
;
// 双方的卡组状态
opExtraDeck
:
ExtraDeckState
;
// 对手的额外卡组状态
meTimeLimit
?:
TimeLimit
;
// 自己的计时
extraDeck
:
CardsBothSide
<
ExtraDeckState
>
;
// 双方的额外卡组状态
opTimeLimit
?:
TimeLimit
;
// 对手的计时
timeLimit
:
BothSide
<
number
>
;
// 双方的时间限制
hint
:
HintState
;
hint
:
HintState
;
...
@@ -42,6 +48,8 @@ export interface PlayMatState {
...
@@ -42,6 +48,8 @@ export interface PlayMatState {
waiting
:
boolean
;
waiting
:
boolean
;
unimplemented
:
number
;
// 未处理的`Message`
unimplemented
:
number
;
// 未处理的`Message`
// remove: (player: number, sequence: number) => void;
}
}
export
interface
InitInfo
{
export
interface
InitInfo
{
...
@@ -51,14 +59,18 @@ export interface InitInfo {
...
@@ -51,14 +59,18 @@ export interface InitInfo {
extraSize
:
number
;
extraSize
:
number
;
}
}
/**
* 场上某位置的状态,
* 以后会更名为 BlockState
*/
export
interface
CardState
{
export
interface
CardState
{
occupant
?:
CardMeta
;
// 占据此位置的卡牌元信息
occupant
?:
CardMeta
;
// 占据此位置的卡牌元信息
location
:
{
location
:
{
controler
?:
number
;
controler
?:
number
;
// 控制这个位置的玩家,0或1
location
:
ygopro
.
CardZone
;
location
:
ygopro
.
CardZone
;
// 怪兽区/魔法陷阱区/手牌/卡组/墓地/除外区
position
?:
ygopro
.
CardPosition
;
position
?:
ygopro
.
CardPosition
;
// 卡片的姿势:攻击还是守备
overlay_sequence
?:
number
;
overlay_sequence
?:
number
;
};
// 位置信息
};
// 位置信息
,叫location的原因是为了和ygo对齐
idleInteractivities
:
Interactivity
<
number
>
[];
// IDLE状态下的互动信息
idleInteractivities
:
Interactivity
<
number
>
[];
// IDLE状态下的互动信息
placeInteractivities
?:
Interactivity
<
{
placeInteractivities
?:
Interactivity
<
{
controler
:
number
;
controler
:
number
;
...
@@ -70,9 +82,10 @@ export interface CardState {
...
@@ -70,9 +82,10 @@ export interface CardState {
reload
?:
boolean
;
// 这个字段会在收到MSG_RELOAD_FIELD的时候设置成true,在收到MSG_UPDATE_DATE的时候设置成false
reload
?:
boolean
;
// 这个字段会在收到MSG_RELOAD_FIELD的时候设置成true,在收到MSG_UPDATE_DATE的时候设置成false
}
}
export
interface
DuelFieldState
{
/**
inner
:
CardState
[];
* CardState的顺序index,被称为sequence
}
*/
export
type
DuelFieldState
=
CardState
[];
export
interface
Interactivity
<
T
>
{
export
interface
Interactivity
<
T
>
{
interactType
:
InteractType
;
interactType
:
InteractType
;
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment