/// <summary> /// new load or re-load. /// this control must already be added to the viewer (DiagramViewer). /// It generates ports for all variables /// </summary> /// <param name="data">the result of lower level editing</param> public void LoadData(IMathExpression data) { bLoading = true; DiagramViewer dv = this.Parent as DiagramViewer; VariableList currentVariables = null; IVariable currOutVar = null; if (mathExp != null) { currOutVar = mathExp.OutputVariable; currentVariables = mathExp.InputVariables; } mathExp = data; if (mathExp == null) { mathExp = new MathNodeRoot(); } mathExp.ClearFocus(); //1. find out all unique and non-local variables VariableList _portVariables = mathExp.InputVariables; //2. remove removed ports if (currentVariables != null) { foreach (IVariable v in currentVariables) { if (_portVariables.GetVariableById(v.ID) == null) { //remove port and nodes List <Control> cs = new List <Control>(); foreach (Control c in dv.Controls) { LinkLineNodeInPort p = c as LinkLineNodeInPort; if (p != null) { if (p.PortID == v.ID) { cs.Add(p); cs.Add(p.Label); ILinkLineNode prev = p.PrevNode; while (prev != null) { if (prev is LinkLineNodePort) { break; } cs.Add((Control)prev); prev = prev.PrevNode; } break; } } } foreach (Control c in cs) { dv.Controls.Remove(c); } } } } List <Control> newControls = new List <Control>(); List <LinkLineNodeInPort> newInPorts = new List <LinkLineNodeInPort>(); //3.create new ports foreach (IVariable v in _portVariables) { if (currentVariables == null || currentVariables.GetVariableById(v.ID) == null) { if (data.IsContainer) { //create a new variable instance MathNodeRoot r = new MathNodeRoot(); ((MathNode)v).root.CopyAttributesToTarget(r); r[1] = new MathNodeVariable(r); IVariable vi = (IVariable)r[1]; vi.VariableType = (RaisDataType)v.VariableType.Clone(); vi.VariableName = v.VariableName; vi.SubscriptName = v.SubscriptName; vi.ResetID(v.ID); vi.InPort = new LinkLineNodeInPort(vi); vi.InPort.SetPortOwner(vi); vi.InPort.Owner = this; newControls.Add(vi.InPort); newControls.Add(vi.InPort.Label); vi.InPort.CheckCreatePreviousNode(); newControls.Add((Control)vi.InPort.PrevNode); newInPorts.Add(vi.InPort); } else { v.InPort = new LinkLineNodeInPort(v); v.InPort.Owner = this; newControls.Add(v.InPort); newControls.Add(v.InPort.Label); v.InPort.CheckCreatePreviousNode(); newControls.Add((Control)v.InPort.PrevNode); newInPorts.Add(v.InPort); } } } if (newInPorts.Count > 0) { int dn = this.Width / (newInPorts.Count + 1); for (int i = 0; i < newInPorts.Count; i++) { newInPorts[i].Position = i * dn + dn; newInPorts[i].Left = this.Left + newInPorts[i].Position; newInPorts[i].SaveLocation(); newInPorts[i].PrevNode.Left = newInPorts[i].Left; } } //3. re-map to existing ports if (currOutVar != null && currOutVar.OutPorts != null) { //if port exists then re-use it mathExp.OutputVariable.OutPorts = currOutVar.OutPorts; for (int i = 0; i < mathExp.OutputVariable.OutPorts.Length; i++) { mathExp.OutputVariable.OutPorts[i].SetPortOwner(mathExp.OutputVariable); //if linking exists then re-establish it if (currOutVar.OutPorts[i].LinkedPortID != 0) { //find the variable if (dv != null) { IVariable v = dv.FindVariableById(currOutVar.OutPorts[i].LinkedPortID); if (v != null) { v.InPort.LinkedPortID = mathExp.OutputVariable.ID; } } } } } else { //for a new load, create the output port mathExp.OutputVariable.OutPorts = new LinkLineNodeOutPort[] { new LinkLineNodeOutPort(mathExp.OutputVariable) }; mathExp.OutputVariable.OutPorts[0].CheckCreateNextNode(); ////use the default position mathExp.OutputVariable.OutPorts[0].Position = this.Width / 2; } for (int i = 0; i < mathExp.OutputVariable.OutPorts.Length; i++) { mathExp.OutputVariable.OutPorts[i].Owner = this; mathExp.OutputVariable.OutPorts[i].Label.Visible = false; mathExp.OutputVariable.OutPorts[i].SaveLocation(); } if (!(currOutVar != null && currOutVar.OutPorts != null)) { for (int i = 0; i < mathExp.OutputVariable.OutPorts.Length; i++) { //for a new load, set default postion for the empty linking node ((Control)(mathExp.OutputVariable.OutPorts[i].NextNode)).Location = mathExp.OutputVariable.OutPorts[i].DefaultNextNodePosition(); //add new controls newControls.Add(mathExp.OutputVariable.OutPorts[i]); newControls.Add((Control)mathExp.OutputVariable.OutPorts[i].NextNode); newControls.Add(mathExp.OutputVariable.OutPorts[i].Label); } } //add the new controls if (this.Parent != null && newControls.Count > 0) { Control[] a = new Control[newControls.Count]; newControls.CopyTo(a); this.Parent.Controls.AddRange(a); } mathExp.PrepareDrawInDiagram(); // createImage(); bLoading = false; }