using UnityEngine; using UnityEngine.UI; using System; /// /// 考核弹窗:选择题 + 操作确认。 /// 回调返回 proportion (0~1 得分比例) 和 feedback。 /// public class ExamPopup : MonoBehaviour { [Header("UI 组件")] [SerializeField] private GameObject _popupRoot; [SerializeField] private Text _questionText; [SerializeField] private Toggle[] _optionToggles; [SerializeField] private Text[] _optionLabels; [SerializeField] private Button _confirmButton; [SerializeField] private Text _feedbackText; [Header("操作题 UI")] [SerializeField] private GameObject _operationPanel; [SerializeField] private Text _operationHint; private StepData _currentStep; private Action _onAnswerCallback; private int _selectedIndex = -1; private void Awake() { if (_confirmButton) _confirmButton.onClick.AddListener(OnConfirm); if (_popupRoot != null) _popupRoot.SetActive(false); } public void Show(StepData step, Action onAnswer) { _currentStep = step; _onAnswerCallback = onAnswer; _selectedIndex = -1; if (_feedbackText != null) _feedbackText.text = ""; if (_popupRoot != null) _popupRoot.SetActive(true); if (_questionText != null) _questionText.text = step.ExamQuestionText; switch (step.CompleteType) { case StepCompleteType.MultipleChoice: SetupMultipleChoice(step); break; case StepCompleteType.ClickObject: SetupClickObject(step); break; case StepCompleteType.SequenceClick: SetupSequenceClick(step); break; default: SetupDefault(step); break; } } private void SetupMultipleChoice(StepData step) { if (_operationPanel != null) _operationPanel.SetActive(false); int optionCount = step.ExamOptions != null ? step.ExamOptions.Length : 0; for (int i = 0; i < (_optionToggles != null ? _optionToggles.Length : 0); i++) { bool active = i < optionCount; _optionToggles[i].gameObject.SetActive(active); _optionToggles[i].isOn = false; _optionToggles[i].onValueChanged.RemoveAllListeners(); int idx = i; _optionToggles[i].onValueChanged.AddListener((val) => { if (val) _selectedIndex = idx; }); if (active && _optionLabels != null && i < _optionLabels.Length) _optionLabels[i].text = step.ExamOptions[i]; } if (_confirmButton != null) _confirmButton.gameObject.SetActive(true); } private void SetupClickObject(StepData step) { if (_operationPanel != null) _operationPanel.SetActive(true); if (_optionToggles != null) foreach (var t in _optionToggles) t.gameObject.SetActive(false); if (_confirmButton != null) _confirmButton.gameObject.SetActive(true); if (_operationHint != null) _operationHint.text = "请点击场景中的 " + step.TargetTag + " 物体"; } private void SetupSequenceClick(StepData step) { if (_operationPanel != null) _operationPanel.SetActive(true); if (_optionToggles != null) foreach (var t in _optionToggles) t.gameObject.SetActive(false); if (_confirmButton != null) _confirmButton.gameObject.SetActive(true); if (_operationHint != null) _operationHint.text = "请按正确顺序点击物体,完成后按确定"; } private void SetupDefault(StepData step) { if (_operationPanel != null) _operationPanel.SetActive(false); if (_optionToggles != null) foreach (var t in _optionToggles) t.gameObject.SetActive(false); if (_confirmButton != null) _confirmButton.gameObject.SetActive(true); } private void OnConfirm() { if (_currentStep == null) return; float proportion = 1f; string feedback = ""; if (_currentStep.CompleteType == StepCompleteType.MultipleChoice) { bool correct = _selectedIndex == _currentStep.CorrectOptionIndex; proportion = correct ? 1f : 0f; feedback = correct ? "" : _currentStep.ErrorFeedback; if (!correct && _feedbackText != null) _feedbackText.text = feedback; } _onAnswerCallback?.Invoke(proportion, feedback); Hide(); } public void Hide() { if (_popupRoot != null) _popupRoot.SetActive(false); _currentStep = null; _onAnswerCallback = null; } }