private void onTypeSelected(object sender, EventArgs e) { guiValueTxt.Visible = false; guiValueCbo.Visible = false; TalkTreeFlag talkTreeFlag = (TalkTreeFlag)guiTypeCbo.SelectedItem; switch (talkTreeFlag) { case TalkTreeFlag.Mission_Goto_Stage: guiValueCbo.Items.Clear(); if (m_parentForm.getStages() != null && m_parentForm.getStages().Count != 0) { guiValueCbo.Items.AddRange(m_parentForm.getStages().ToArray()); //guiValueCbo.Items.Add(CodeValue.Formatted(-2, "Repeatable mission")); guiValueCbo.Items.Add(new CodeValue(-2, "Mission completed & is repeatable")); if (guiValueTxt.Text.Length == 0) { guiValueCbo.SelectedIndex = 0; } else { guiValueCbo.SelectedItem = new CodeValue(Int32.Parse(guiValueTxt.Text)); } } guiValueCbo.Visible = true; break; default: guiValueTxt.Text = ""; break; } if (m_treeNode != null) { TalkNode talkNode = (TalkNode)m_treeNode.Tag; talkNode.text = ((int)talkTreeFlag).ToString(); talkNode.id = guiValueTxt.Text; m_treeNode.Text = talkNode.ToString(); } }
public Boolean validate(out String error) { // Verify that first node does not contain Trade // Check that each text field is non-empty // Verify that each node has a unique ID // Verify that each branch leads to a valid <Tree> node // TODO: Prune unused <Tree> nodes TalkNode npcTalkNode; TalkNode replyTalkNode; int nodeId = 1; error = ""; List <String> idList = new List <string>(); List <CheckBranch> branchList = new List <CheckBranch>(); TalkTreeFlag talkTreeFlag = TalkTreeFlag.More; if (guiTalkTree.Nodes.Count == 0) { // Valid to have an empty talk tree since could be removing it } foreach (TreeNode npcTreeNode in guiTalkTree.Nodes) { npcTalkNode = (TalkNode)npcTreeNode.Tag; if (idList.Contains(npcTalkNode.id)) { error = "The node id '" + npcTalkNode.id + "' is present more than once"; return(false); } else { idList.Add(npcTalkNode.id); } if (nodeId == 1) { if (!npcTalkNode.id.Equals("1")) { error = "The first node has an id of '" + npcTalkNode.id + "' but was expected to have the id '1'"; return(false); } else { foreach (TreeNode replyTreeNode in npcTreeNode.Nodes) { replyTalkNode = (TalkNode)replyTreeNode.Tag; if (replyTalkNode.type.Equals(TalkNodeTypes.Flags)) { if (!Enumeration.TryParse <TalkTreeFlag>(replyTalkNode.text, out talkTreeFlag)) { // If cannot parse the value then put it to something different than Trade // to avoid erronously reporting an error here. The parse error will be // reported below. talkTreeFlag = TalkTreeFlag.More; } } if (replyTalkNode.type.Equals(TalkNodeTypes.Trade) || (replyTalkNode.type.Equals(TalkNodeTypes.Flags) && talkTreeFlag.Equals(TalkTreeFlag.Trade))) { error = "The first node cannot specify a trade action"; return(false); } } } } // First node if (npcTalkNode.text.Length == 0) { error = "The node '" + npcTalkNode.id + "' does not specify any NPC text"; return(false); } if (npcTreeNode.Nodes.Count == 0) { error = "The node '" + npcTalkNode.id + "' does not specify any reply"; return(false); } foreach (TreeNode childTreeNode in npcTreeNode.Nodes) { replyTalkNode = (TalkNode)childTreeNode.Tag; switch (replyTalkNode.type) { case TalkNodeTypes.None: break; case TalkNodeTypes.Branch: if (npcTalkNode.id.Equals(replyTalkNode.id)) { error = "Cannot branch to the same/current node (Node: " + npcTalkNode.id + ")"; return(false); } branchList.Add(new CheckBranch(npcTalkNode.id, replyTalkNode.id)); if (replyTalkNode.text.Length == 0) { error = "A branch does not specify any text (Node: " + npcTalkNode.id + ")"; return(false); } break; case TalkNodeTypes.Trade: break; case TalkNodeTypes.Flags: { if (!Enumeration.TryParse <TalkTreeFlag>(replyTalkNode.text, out talkTreeFlag)) { error = "The flag value '" + replyTalkNode.text + "' cannot be converted to a TalkTreeFlag value (Node: " + npcTalkNode.id + ")"; return(false); } else { switch (talkTreeFlag) { case TalkTreeFlag.Mission_Goto_Stage: if (replyTalkNode.id.Equals("0")) { error = "Cannot go back to stage 0 (Node: " + npcTalkNode.id + ")"; return(false); } else if (replyTalkNode.id.Equals("-2")) { // This is not an error but is needed to prevent // the next validation from reporting an error } else { error = "The " + TalkTreeFlag.Mission_Goto_Stage.ToString() + " flag points to an invalid stage ID of '" + replyTalkNode.id + "' (Node: " + npcTalkNode.id + ")"; if (m_stages != null) { foreach (CodeValue stage in m_stages) { if (stage.code.ToString().Equals(replyTalkNode.id)) { error = ""; break; } } } if (error.Length != 0) { return(false); } } break; } } } // case TalkNodeTypes.Flags break; } // switch(replyTalkNode.type) ++nodeId; } // foreach (TreeNode childTreeNode in npcTreeNode.Nodes) } // foreach NPC node // Validate that each branch has a valid destination foreach (CheckBranch checkGoto in branchList) { if (!idList.Contains(checkGoto.branchToNodeId)) { error = "The branch directs to an invalid node id '" + checkGoto.branchToNodeId + "' (Node: " + checkGoto.npcTreeNodeId + ")"; return(false); } } // Validate that each npc node is accessed branchList.Add(new CheckBranch("1", "1")); // Node 1 has an implicit branch-to access foreach (CheckBranch checkBranch in branchList) { idList.Remove(checkBranch.branchToNodeId); } if (idList.Count != 0) { error = "Node " + idList[0] + " cannot be accessed"; return(false); } return(true); } // validate()