功能:記分板語音改為報比分、發球區、賽末點與獲勝隊伍
摘要: - 得分播報改為「比分(發球方先報)+ 發球者左右發球區」 - 發球方到賽末點(再得 1 分即獲勝)時,比分後加唸「賽末點」 - 賽末點得分獲勝時,整段改播「<獲勝隊伍> 贏得比賽」 - 發球區左右一律用實際球場方向,取消上方隊伍鏡像;畫面「發球區」顯示同步改為不鏡像,與語音一致 根本原因: - 現場記分需要即時聽到比分與發球位置,原本只唸「誰得分、誰發球」較不直覺 - 先前發球區對上方隊伍做鏡像,導致語音與實際球場方向相反 影響: - src/App.tsx:recordPoint 計算發球方比分、發球區、賽末點與獲勝隊伍,重整 voiceAnnouncement 欄位 - src/pages/ScoreboardPage.tsx:語音組字改為「X比Y(賽末點)」「OO左/右邊發球」、獲勝改播「贏得比賽」;發球區顯示移除鏡像;語音設定「播報誰得分」更名「播報比分」 修法: - 發球方分數先報;賽末點僅在發球方再得 1 分就獲勝時觸發;發球區統一用 getServiceCourt 實際方向 Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
+12
-5
@@ -89,6 +89,7 @@ type VoiceAnnouncement = {
|
||||
opponentScore: number
|
||||
serverName: string
|
||||
serverCourt: 'left' | 'right'
|
||||
matchPoint: boolean
|
||||
winnerTeamName: string | null
|
||||
}
|
||||
|
||||
@@ -773,13 +774,18 @@ function App() {
|
||||
: getTeamDisplayName(rightTeam)
|
||||
: null
|
||||
|
||||
// 得分方接著發球,報分以發球方分數為先;左側隊伍的發球區需鏡像對應畫面。
|
||||
// 得分方接著發球,報分以發球方分數為先;發球區一律用實際球場左右,不做鏡像。
|
||||
const servingScore = side === 'left' ? nextScoreState.scoreLeft : nextScoreState.scoreRight
|
||||
const opponentScore = side === 'left' ? nextScoreState.scoreRight : nextScoreState.scoreLeft
|
||||
const serverCourt =
|
||||
side === 'left'
|
||||
? getMirroredCourt(getServiceCourt(servingScore))
|
||||
: getServiceCourt(servingScore)
|
||||
const serverCourt = getServiceCourt(servingScore)
|
||||
// 只有發球方(剛得分那隊)再得 1 分就能贏,才算賽末點。
|
||||
const matchPoint =
|
||||
!reachedTarget &&
|
||||
hasWonGame(
|
||||
side === 'left'
|
||||
? { ...nextScoreState, scoreLeft: nextScoreState.scoreLeft + 1 }
|
||||
: { ...nextScoreState, scoreRight: nextScoreState.scoreRight + 1 },
|
||||
)
|
||||
|
||||
setScoreHistory((current) => [...current, { pointLog, scoreState }])
|
||||
setPointLog(nextPointLog)
|
||||
@@ -790,6 +796,7 @@ function App() {
|
||||
opponentScore,
|
||||
serverName: getNextServerName(nextScoreState, leftTeam, rightTeam, side),
|
||||
serverCourt,
|
||||
matchPoint,
|
||||
winnerTeamName,
|
||||
})
|
||||
|
||||
|
||||
@@ -3,7 +3,6 @@ import { useEffect, useMemo, useRef, useState } from 'react'
|
||||
import { Link } from 'react-router-dom'
|
||||
import {
|
||||
getCourtAssignments,
|
||||
getMirroredCourt,
|
||||
getReceivingPlayer,
|
||||
getServiceCourt,
|
||||
getServingPlayer,
|
||||
@@ -64,6 +63,7 @@ type ScoreboardPageProps = {
|
||||
opponentScore: number
|
||||
serverName: string
|
||||
serverCourt: 'left' | 'right'
|
||||
matchPoint: boolean
|
||||
winnerTeamName: string | null
|
||||
} | null
|
||||
targetDate: string
|
||||
@@ -260,7 +260,11 @@ export function ScoreboardPage({
|
||||
const parts: string[] = []
|
||||
|
||||
if (voiceSettings.announceScore) {
|
||||
parts.push(`${voiceAnnouncement.servingScore}比${voiceAnnouncement.opponentScore}`)
|
||||
parts.push(
|
||||
`${voiceAnnouncement.servingScore}比${voiceAnnouncement.opponentScore}${
|
||||
voiceAnnouncement.matchPoint ? ' 賽末點' : ''
|
||||
}`,
|
||||
)
|
||||
}
|
||||
|
||||
if (voiceSettings.announceServer && voiceAnnouncement.serverName) {
|
||||
@@ -484,11 +488,7 @@ export function ScoreboardPage({
|
||||
onSwapPlayers={() => onSwapTeamPlayers('left')}
|
||||
onSwapTeams={onSwapMatchup}
|
||||
score={scoreState.scoreLeft}
|
||||
serviceCourt={
|
||||
scoreState.serving === 'left' && servingCourt
|
||||
? getMirroredCourt(servingCourt)
|
||||
: null
|
||||
}
|
||||
serviceCourt={scoreState.serving === 'left' ? servingCourt : null}
|
||||
showServingPrompt={scoreState.serving === null}
|
||||
team={leftTeam}
|
||||
teamSlot="top"
|
||||
|
||||
Reference in New Issue
Block a user