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
6fc21e22
Commit
6fc21e22
authored
May 19, 2023
by
Chunchi Che
Browse files
Options
Browse Files
Download
Plain Diff
Merge branch 'feat/service/chain' into 'main'
Feat/service/chain See merge request
!198
parents
7bc9f266
e37fe4ad
Changes
12
Hide whitespace changes
Inline
Side-by-side
Showing
12 changed files
with
77 additions
and
36 deletions
+77
-36
src/api/cards.ts
src/api/cards.ts
+6
-14
src/api/strings.ts
src/api/strings.ts
+1
-1
src/infra/stream.ts
src/infra/stream.ts
+5
-0
src/service/duel/chainSolved.ts
src/service/duel/chainSolved.ts
+10
-1
src/service/duel/chaining.ts
src/service/duel/chaining.ts
+9
-3
src/service/duel/move.ts
src/service/duel/move.ts
+10
-2
src/service/duel/sortCard.ts
src/service/duel/sortCard.ts
+1
-1
src/stores/matStore/methods/fetchHint.ts
src/stores/matStore/methods/fetchHint.ts
+1
-1
src/stores/matStore/store.ts
src/stores/matStore/store.ts
+23
-7
src/stores/matStore/types.ts
src/stores/matStore/types.ts
+9
-2
src/styles/core.scss
src/styles/core.scss
+0
-4
src/ui/Duel/Message/CardListModal.tsx
src/ui/Duel/Message/CardListModal.tsx
+2
-0
No files found.
src/api/cards.ts
View file @
6fc21e22
...
...
@@ -49,20 +49,12 @@ export interface CardText {
* @returns 卡片数据
*
* */
export
async
function
fetchCard
(
id
:
number
,
local
:
boolean
=
true
):
Promise
<
CardMeta
>
{
if
(
local
)
{
const
res
=
await
sqliteMiddleWare
({
cmd
:
sqliteCmd
.
SELECT
,
payload
:
{
id
},
});
return
res
.
selectResult
?
res
.
selectResult
:
{
id
,
data
:
{},
text
:
{}
};
}
const
res
=
await
axios
.
get
<
CardMeta
>
(
"
http://localhost:3030/cards/
"
+
id
);
return
res
.
data
;
export
async
function
fetchCard
(
id
:
number
):
Promise
<
CardMeta
>
{
const
res
=
await
sqliteMiddleWare
({
cmd
:
sqliteCmd
.
SELECT
,
payload
:
{
id
},
});
return
res
.
selectResult
?
res
.
selectResult
:
{
id
,
data
:
{},
text
:
{}
};
}
export
function
getCardStr
(
meta
:
CardMeta
,
idx
:
number
):
string
|
undefined
{
...
...
src/api/strings.ts
View file @
6fc21e22
...
...
@@ -30,6 +30,6 @@ export async function getStrings(description: number): Promise<string> {
const
code
=
description
>>
4
;
const
index
=
description
&
0xf
;
return
getCardStr
(
await
fetchCard
(
code
,
true
),
index
)
||
""
;
return
getCardStr
(
await
fetchCard
(
code
),
index
)
||
""
;
}
}
src/infra/stream.ts
View file @
6fc21e22
// web平台上websocket的消息到达是保序的,但是不能保证对这些消息的逻辑处理是保序的。
// 现在我们有这样一个需求:需要保证每次只处理一个消息,在上一个消息处理完后,再进行下一个消息的处理。
//
// 因此封装了一个`WebSocketStream`类,当每次Websocket连接中有消息到达时,往流中添加event,
// 同时执行器会不断地从流中获取event进行处理。
import
{
sleep
}
from
"
./sleep
"
;
const
SLEEP_INTERVAL
=
200
;
...
...
src/service/duel/chainSolved.ts
View file @
6fc21e22
import
{
ygopro
}
from
"
@/api
"
;
import
{
matStore
}
from
"
@/stores
"
;
export
default
(
chainSolved
:
ygopro
.
StocGameMessage
.
MsgChainSolved
)
=>
{
console
.
log
(
chainSolved
);
const
location
=
matStore
.
chains
.
splice
(
chainSolved
.
solved_index
-
1
,
1
)
.
at
(
0
);
if
(
location
)
{
// 设置被连锁状态为空
matStore
.
setChained
(
location
,
undefined
);
}
else
{
console
.
warn
(
"
pop from chains return null!
"
);
}
};
src/service/duel/chaining.ts
View file @
6fc21e22
...
...
@@ -9,9 +9,15 @@ export default async (chaining: ygopro.StocGameMessage.MsgChaining) => {
cardID
:
chaining
.
code
,
});
matStore
.
setChaining
(
chaining
.
location
,
chaining
.
code
,
true
);
await
matStore
.
setChaining
(
chaining
.
location
,
chaining
.
code
,
true
);
await
sleep
(
useConfig
().
ui
.
chainingDelay
);
matStore
.
setChaining
(
chaining
.
location
,
chaining
.
code
,
false
);
// TODO: set chained
const
location
=
chaining
.
location
;
// 恢复成非`chaining`状态
await
matStore
.
setChaining
(
location
,
chaining
.
code
,
false
);
// 将`location`添加到连锁栈
matStore
.
chains
.
push
(
location
);
// 设置被连锁状态
matStore
.
setChained
(
location
,
matStore
.
chains
.
length
);
};
src/service/duel/move.ts
View file @
6fc21e22
...
...
@@ -22,6 +22,7 @@ export default async (move: MsgMove) => {
// FIXME: 考虑超量素材的情况
let
uuid
;
let
chainIndex
;
switch
(
from
.
location
)
{
case
ygopro
.
CardZone
.
MZONE
:
case
ygopro
.
CardZone
.
SZONE
:
{
...
...
@@ -32,6 +33,7 @@ export default async (move: MsgMove) => {
target
.
occupant
=
undefined
;
target
.
overlay_materials
=
[];
uuid
=
target
.
uuid
;
chainIndex
=
target
.
chainIndex
;
// 需要重新分配UUID
target
.
uuid
=
v4uuid
();
break
;
...
...
@@ -47,6 +49,7 @@ export default async (move: MsgMove) => {
.
of
(
from
.
controler
)
.
remove
(
from
.
sequence
);
uuid
=
removed
.
uuid
;
chainIndex
=
removed
.
chainIndex
;
break
;
}
...
...
@@ -77,8 +80,12 @@ export default async (move: MsgMove) => {
.
of
(
to
.
controler
)
.
setOccupant
(
to
.
sequence
,
code
,
to
.
position
,
true
);
if
(
uuid
)
{
// 设置UUID
matStore
.
in
(
to
.
location
).
of
(
to
.
controler
)[
to
.
sequence
].
uuid
=
uuid
;
}
// 设置连锁序号
matStore
.
in
(
to
.
location
).
of
(
to
.
controler
)[
to
.
sequence
].
chainIndex
=
chainIndex
;
await
sleep
(
NeosConfig
.
ui
.
moveDelay
);
matStore
.
in
(
to
.
location
).
of
(
to
.
controler
)[
to
.
sequence
].
focus
=
false
;
...
...
@@ -92,7 +99,7 @@ export default async (move: MsgMove) => {
matStore
.
in
(
to
.
location
)
.
of
(
to
.
controler
)
.
insert
(
uuid
,
code
,
to
.
sequence
,
to
.
position
);
.
insert
(
uuid
,
code
,
to
.
sequence
,
to
.
position
,
false
,
chainIndex
);
}
break
;
}
...
...
@@ -106,7 +113,8 @@ export default async (move: MsgMove) => {
code
,
to
.
sequence
,
ygopro
.
CardPosition
.
FACEUP_ATTACK
,
true
true
,
chainIndex
);
await
sleep
(
NeosConfig
.
ui
.
moveDelay
);
...
...
src/service/duel/sortCard.ts
View file @
6fc21e22
...
...
@@ -6,7 +6,7 @@ type MsgSortCard = ygopro.StocGameMessage.MsgSortCard;
export
default
async
(
sortCard
:
MsgSortCard
)
=>
{
await
Promise
.
all
(
sortCard
.
options
.
map
(
async
({
code
,
response
})
=>
{
const
meta
=
await
fetchCard
(
code
!
,
true
);
const
meta
=
await
fetchCard
(
code
!
);
messageStore
.
sortCardModal
.
options
.
push
({
meta
,
response
:
response
!
,
...
...
src/stores/matStore/methods/fetchHint.ts
View file @
6fc21e22
...
...
@@ -21,7 +21,7 @@ export const fetchSelectHintMeta = async ({
let
selectHintMeta
=
""
;
if
(
selectHintData
>
DESCRIPTION_LIMIT
)
{
// 针对`MSG_SELECT_PLACE`的特化逻辑
const
cardMeta
=
await
fetchCard
(
selectHintData
,
true
);
const
cardMeta
=
await
fetchCard
(
selectHintData
);
selectHintMeta
=
fetchStrings
(
"
!system
"
,
569
).
replace
(
"
[%ls]
"
,
cardMeta
.
text
.
name
||
"
[?]
"
...
...
src/stores/matStore/store.ts
View file @
6fc21e22
...
...
@@ -31,10 +31,11 @@ class CardArray extends Array<CardState> implements ArrayCardState {
controller
:
number
,
id
:
number
,
position
?:
ygopro
.
CardPosition
,
focus
?:
boolean
focus
?:
boolean
,
chainIndex
?:
number
)
=>
({
uuid
,
occupant
:
await
fetchCard
(
id
,
true
),
occupant
:
await
fetchCard
(
id
),
location
:
{
controler
:
controller
,
zone
:
this
.
zone
,
...
...
@@ -43,6 +44,7 @@ class CardArray extends Array<CardState> implements ArrayCardState {
},
focus
:
focus
??
false
,
chaining
:
false
,
chainIndex
,
directAttack
:
false
,
counters
:
{},
idleInteractivities
:
[],
...
...
@@ -56,14 +58,16 @@ class CardArray extends Array<CardState> implements ArrayCardState {
id
:
number
,
sequence
:
number
,
position
?:
ygopro
.
CardPosition
,
focus
?:
boolean
focus
?:
boolean
,
chainIndex
?:
number
)
{
const
card
=
await
this
.
genCard
(
uuid
,
this
.
getController
(),
id
,
position
,
focus
focus
,
chainIndex
);
this
.
splice
(
sequence
,
0
,
card
);
}
...
...
@@ -234,6 +238,8 @@ export const matStore: MatState = proxy<MatState>({
decks
:
genDuelCardArray
([],
DECK
),
extraDecks
:
genDuelCardArray
([],
EXTRA
),
chains
:
[],
timeLimits
:
{
// 时间限制
me
:
-
1
,
...
...
@@ -262,15 +268,17 @@ export const matStore: MatState = proxy<MatState>({
// methods
in
:
getZone
,
isMe
,
setChaining
(
location
,
code
,
isChaining
)
{
async
setChaining
(
location
,
code
,
isChaining
)
{
const
target
=
this
.
in
(
location
.
location
)
.
of
(
location
.
controler
)
.
at
(
location
.
sequence
);
if
(
target
)
{
target
.
chaining
=
isChaining
;
if
(
target
.
occupant
&&
isChaining
)
{
// 目前需要判断`isChaining`为ture才设置id,因为有些手坑发效果后会move到墓地,运行到这里的时候已经和原来的位置对不上了,这时候不设置id
target
.
occupant
.
id
=
code
;
// 目前需要判断`isChaining`为ture才设置meta,因为有些手坑发效果后会move到墓地,
// 运行到这里的时候已经和原来的位置对不上了,这时候不设置meta
const
meta
=
await
fetchCard
(
code
);
target
.
occupant
=
meta
;
}
if
(
target
.
location
.
zone
==
ygopro
.
CardZone
.
HAND
)
{
target
.
location
.
position
=
isChaining
...
...
@@ -279,6 +287,14 @@ export const matStore: MatState = proxy<MatState>({
}
}
},
setChained
(
location
,
chainIndex
)
{
const
target
=
this
.
in
(
location
.
location
)
.
of
(
location
.
controler
)
.
at
(
location
.
sequence
);
if
(
target
)
{
target
.
chainIndex
=
chainIndex
;
}
},
});
// @ts-ignore 挂到全局,便于调试
...
...
src/stores/matStore/types.ts
View file @
6fc21e22
...
...
@@ -21,7 +21,8 @@ export interface DuelFieldState extends Array<CardState> {
id
:
number
,
sequence
:
number
,
position
?:
ygopro
.
CardPosition
,
focus
?:
boolean
focus
?:
boolean
,
chainIndex
?:
number
)
=>
Promise
<
void
>
;
/** 在末尾添加卡片 */
add
:
(
...
...
@@ -78,6 +79,8 @@ export interface MatState {
extraDecks
:
BothSide
<
ExtraDeckState
>
;
// 双方的额外卡组状态
chains
:
ygopro
.
CardLocation
[];
// 连锁的卡片位置
timeLimits
:
BothSide
<
number
>
&
{
set
:
(
controller
:
number
,
time
:
number
)
=>
void
;
};
// 双方的时间限制
...
...
@@ -108,7 +111,9 @@ export interface MatState {
location
:
ygopro
.
CardLocation
,
code
:
number
,
isChaining
:
boolean
)
=>
void
;
)
=>
Promise
<
void
>
;
// 添加被连锁状态
setChained
:
(
location
:
ygopro
.
CardLocation
,
chainIndex
?:
number
)
=>
void
;
}
export
interface
InitInfo
{
...
...
@@ -132,6 +137,8 @@ export interface CardState {
};
// 位置信息,叫location的原因是为了和ygo对齐
focus
:
boolean
;
// 用于实现动画效果,当这个字段为true时,该张卡片会被放大并在屏幕中央展示
chaining
:
boolean
;
// 是否在连锁中
chainIndex
?:
number
/*连锁的序号,如果为空表示不在连锁
TODO: 目前是妥协的设计,因为其实一张卡是可以在同一个连锁链中被连锁多次的,这里为了避免太过复杂只保存最后的连锁序号*/
;
directAttack
:
boolean
;
// 是否正在直接攻击为玩家
attackTarget
?:
CardState
&
{
sequence
:
number
;
opponent
:
boolean
};
// 攻击目标。(嵌套结构可行么?)
idleInteractivities
:
Interactivity
<
number
>
[];
// IDLE状态下的互动信息
...
...
src/styles/core.scss
View file @
6fc21e22
...
...
@@ -76,10 +76,6 @@ p {
}
.container
{
// left: 50%;
// position: fixed;
// top: 50%;
// transform: translate(-50%, -50%);
margin
:
0
auto
;
width
:
100%
;
max-width
:
300px
;
...
...
src/ui/Duel/Message/CardListModal.tsx
View file @
6fc21e22
...
...
@@ -48,6 +48,8 @@ export const CardListModal = () => {
}
onClick=
{
()
=>
{
messageStore
.
cardModal
.
meta
=
item
.
meta
;
messageStore
.
cardModal
.
interactivies
=
item
.
interactivies
;
messageStore
.
cardModal
.
counters
=
[];
messageStore
.
cardModal
.
isOpen
=
true
;
}
}
>
...
...
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