diff --git a/frontend-sba/components/Gameplay/GameplayPanel.vue b/frontend-sba/components/Gameplay/GameplayPanel.vue index 30c5ef8..09ddb73 100644 --- a/frontend-sba/components/Gameplay/GameplayPanel.vue +++ b/frontend-sba/components/Gameplay/GameplayPanel.vue @@ -78,6 +78,24 @@ + +
+
+ + + +
+ Waiting for defense to select x-check result... +
+
+ +
+
import { ref, computed } from 'vue' -import type { RollData, PlayResult, PlayOutcome } from '~/types' +import type { RollData, PlayResult, PlayOutcome, XCheckData } from '~/types' +import { useGameStore } from '~/store/game' import DiceRoller from './DiceRoller.vue' import OutcomeWizard from './OutcomeWizard.vue' import PlayResultDisplay from './PlayResult.vue' +import XCheckWizard from './XCheckWizard.vue' interface Props { gameId: string @@ -117,26 +137,44 @@ interface Props { hasRunners?: boolean // Dice color from home team (hex without #) diceColor?: string + // User's team ID (for determining interactive mode in x-check) + userTeamId?: number | null } const props = withDefaults(defineProps(), { outs: 0, hasRunners: false, diceColor: 'cc0000', // Default red + userTeamId: null, }) const emit = defineEmits<{ rollDice: [] submitOutcome: [{ outcome: PlayOutcome; hitLocation?: string }] dismissResult: [] + submitXCheckResult: [{ resultCode: string; errorResult: string }] }>() +// Store access +const gameStore = useGameStore() + // Local state const error = ref(null) const isSubmitting = ref(false) +// X-Check data from store +const xCheckData = computed(() => gameStore.xCheckData) + +// Determine if current user should have interactive mode +// Uses active_team_id from x-check data (set by backend to indicate which team should interact) +const isXCheckInteractive = computed(() => { + if (!xCheckData.value || !props.userTeamId) return false + // Backend sets active_team_id to indicate which team should have interactive controls + return xCheckData.value.active_team_id === props.userTeamId +}) + // Workflow state computation -type WorkflowState = 'idle' | 'ready_to_roll' | 'rolled' | 'submitted' | 'result' +type WorkflowState = 'idle' | 'ready_to_roll' | 'rolled' | 'submitted' | 'result' | 'x_check_result_pending' const workflowState = computed(() => { // Show result if we have one @@ -144,6 +182,11 @@ const workflowState = computed(() => { return 'result' } + // Show x-check result selection if awaiting + if (gameStore.needsXCheckResult && xCheckData.value) { + return 'x_check_result_pending' + } + // Show submitted/processing state if (isSubmitting.value) { return 'submitted' @@ -167,6 +210,7 @@ const workflowState = computed(() => { const statusClass = computed(() => { if (error.value) return 'status-error' if (workflowState.value === 'result') return 'status-success' + if (workflowState.value === 'x_check_result_pending') return 'status-active' if (workflowState.value === 'submitted') return 'status-processing' if (workflowState.value === 'rolled') return 'status-active' if (workflowState.value === 'ready_to_roll' && props.isMyTurn) return 'status-active' @@ -176,6 +220,9 @@ const statusClass = computed(() => { const statusText = computed(() => { if (error.value) return 'Error' if (workflowState.value === 'result') return 'Play Complete' + if (workflowState.value === 'x_check_result_pending') { + return isXCheckInteractive.value ? 'Select X-Check Result' : 'Waiting for Defense' + } if (workflowState.value === 'submitted') return 'Processing' if (workflowState.value === 'rolled') return 'Enter Outcome' if (workflowState.value === 'ready_to_roll') { @@ -210,6 +257,17 @@ const handleDismissResult = () => { error.value = null emit('dismissResult') } + +const handleXCheckSubmit = (payload: { resultCode: string; errorResult: string }) => { + error.value = null + isSubmitting.value = true + emit('submitXCheckResult', payload) + + // Reset submitting state after a delay + setTimeout(() => { + isSubmitting.value = false + }, 3000) +}