/// <summary> /// Creates a group of all selected components. /// For each eventchannelline connected to the selected components, events will also be visible in the group element /// For each channel connected to the selected components, an in or outputport will be added to the group component /// </summary> /// <param name="idForGroup">The id (name) of the group</param> /// <param name="addToUndoStack">Desition, if the undo-operation should be put on the undo-stack</param> /// <param name="storeGroup">Desition, if the group will be part of the model (stored in the deployment model)</param> /// <returns></returns> private String DoGrouping(String idForGroup, bool addToUndoStack, bool storeGroup) { Boolean noGroupInSelection = true; ArrayList selectedGroupChannelList = new ArrayList(); ArrayList selectedGroupComponentList = new ArrayList(); ArrayList selectedGroupEventChannelList = new ArrayList(); ArrayList selectedGroupEdgeListenerEventChannelList = new ArrayList(); ArrayList selectedGroupEdgeTriggerEventChannelList = new ArrayList(); if (selectedComponentList.Count == 0) { MessageBox.Show(Properties.Resources.GroupingNoItemsSelected, Properties.Resources.GroupingNoItemsSelectedHeader, MessageBoxButton.OK, MessageBoxImage.Error); return ""; } // search for a group in the selection foreach (componentType mc in selectedComponentList) { if (mc.ComponentType == ACS2.componentTypeDataTypes.group) { noGroupInSelection = false; MessageBox.Show(Properties.Resources.GroupingWithSelectedGroups, Properties.Resources.GroupingWithSelectedGroupsHeader, MessageBoxButton.OK, MessageBoxImage.Error); break; } } if (noGroupInSelection == false) return ""; groupComponent newGroup = new groupComponent(); // building a "new" model Asterics.ACS2.componentTypesComponentType newGroupForBundle = new ACS2.componentTypesComponentType(); newGroupForBundle.type = new ACS2.componentType(); newGroupForBundle.type.Value = ACS2.componentTypeDataTypes.group; int counter = 0; string suggestID = ""; /*do { counter++; suggestID = "group" + counter; } while (componentList.ContainsKey(suggestID));*/ bool gExists; do { gExists = false; foreach (componentType ct in deploymentComponentList.Values) { if (ct.id.StartsWith(suggestID)) { counter++; gExists = true; } suggestID = "group" + counter; } } while (gExists); Console.WriteLine("SuggestID is " + suggestID); if (idForGroup != null && idForGroup != "") newGroupForBundle.id = idForGroup; else newGroupForBundle.id = suggestID; // adding the channels and the eventchannels here object[] ports = new object[0]; newGroupForBundle.ports = ports; // find lowest and higest cooridantes to place new group component in the middle int lowestX = 2000; int lowestY = 2000; int highestX = 0; int highestY = 0; if (selectedComponentList.Count > 0) { lowestX = highestX = (Int32)Canvas.GetLeft(selectedComponentList.First().ComponentCanvas); lowestY = highestY = (Int32)Canvas.GetTop(selectedComponentList.First().ComponentCanvas); } // remove selected components from canvas and add to group element foreach (componentType mc in selectedComponentList) { selectedGroupComponentList.Add(mc); if (Canvas.GetLeft(mc.ComponentCanvas) < lowestX) { lowestX = (Int32)Canvas.GetLeft(mc.ComponentCanvas); } else if (Canvas.GetLeft(mc.ComponentCanvas) > highestX) { highestX = (Int32)Canvas.GetLeft(mc.ComponentCanvas); } if (Canvas.GetTop(mc.ComponentCanvas) < lowestY) { lowestY = (Int32)Canvas.GetTop(mc.ComponentCanvas); } else if (Canvas.GetTop(mc.ComponentCanvas) > highestY) { highestY = (Int32)Canvas.GetTop(mc.ComponentCanvas); } // new with grouping rework mc.ComponentCanvas.Visibility = System.Windows.Visibility.Hidden; newGroup.AddedComponentList.AddLast(mc); } /* * search channels which are connected to components which will become a member of the group */ ArrayList foundInsideChannels = new ArrayList(); ArrayList foundEdgeSourceChannels = new ArrayList(); ArrayList foundEdgeTargetChannels = new ArrayList(); foreach (channel ch in deploymentChannelList.Values) { bool sourceSelected = selectedComponentList.Contains(deploymentComponentList[ch.source.component.id]); bool targetSelected = selectedComponentList.Contains(deploymentComponentList[ch.target.component.id]); if (sourceSelected && targetSelected) { foundInsideChannels.Add(ch); } else if (sourceSelected && !targetSelected) { foundEdgeSourceChannels.Add(ch); } else if (!sourceSelected && targetSelected) { foundEdgeTargetChannels.Add(ch); } } foreach (channel ch in foundInsideChannels) { if (canvas.Children.Contains(ch.Line)) { ch.Line.Visibility = System.Windows.Visibility.Hidden; newGroup.AddedChannelsList.AddLast(ch); } } foreach (channel ch in foundEdgeSourceChannels) { if (canvas.Children.Contains(ch.Line)) { ch.Line.Visibility = System.Windows.Visibility.Hidden; newGroup.AddedChannelsList.AddLast(ch); } // Add out Port to the component componentType source = deploymentComponentList[ch.source.component.id]; outputPortType outp = null; foreach (object o in source.PortsList.Values) { if (o is outputPortType) { outputPortType outp1 = (outputPortType)o; if (outp1.portTypeID.Equals(ch.source.port.id)) { outp = outp1; } } } if (outp == null) continue; Asterics.ACS2.outputPortType outPort = new ACS2.outputPortType(); outPort.id = ch.source.component.id + "_" + ch.source.port.id; outPort.description = outp.Description; outPort.dataType = outp.PortDataType; refType refT = new refType(); refT.componentID = ch.source.component.id; refT.portID = ch.source.port.id; outPort.RefPort = refT; if (!newGroupForBundle.PortsList.Contains(outPort.id)) { newGroupForBundle.PortsList.Add(outPort.id, outPort); } } foreach (channel ch in foundEdgeTargetChannels) { if (canvas.Children.Contains(ch.Line)) { ch.Line.Visibility = System.Windows.Visibility.Hidden; newGroup.AddedChannelsList.AddLast(ch); } // Add in Port to the component componentType target = deploymentComponentList[ch.target.component.id]; inputPortType inp = null; foreach (object o in target.PortsList.Values) { if (o is inputPortType) { inputPortType inp1 = (inputPortType)o; if (inp1.portTypeID.Equals(ch.target.port.id)) { inp = inp1; } } } if (inp == null) continue; Asterics.ACS2.inputPortType inPort = new ACS2.inputPortType(); inPort.id = ch.target.component.id + "_" + ch.target.port.id; inPort.description = inp.Description; inPort.dataType = inp.PortDataType; inPort.mustBeConnected = inp.MustBeConnected; refType refT = new refType(); refT.componentID = ch.target.component.id; refT.portID = ch.target.port.id; inPort.RefPort = refT; if (!newGroupForBundle.PortsList.Contains(inPort.id)) { newGroupForBundle.PortsList.Add(inPort.id, inPort); } } /* * search eventchannels which are connected to components which will become a member of the group */ ArrayList foundEdgeListenerEvents = new ArrayList(); ArrayList foundEdgeTriggerEvents = new ArrayList(); foreach (eventChannel ec in eventChannelList) { // search for each event channel on the edge of the group element if (!selectedComponentList.Contains(deploymentComponentList[ec.targets.target.component.id]) && selectedComponentList.Contains(deploymentComponentList[ec.sources.source.component.id])) { foreach (EventTriggerPort etp in deploymentComponentList[ec.sources.source.component.id].EventTriggerList) { ACS2.eventsTypeEventTriggererPortType foundTrigger = new ACS2.eventsTypeEventTriggererPortType(); foundTrigger.id = ec.sources.source.component.id + "_" + etp.EventTriggerId; foundTrigger.description = etp.EventDescription; bool contains = false; foreach (ACS2.eventsTypeEventTriggererPortType etel in foundEdgeTriggerEvents) { if (etel.id.Equals(foundTrigger.id)) { contains = true; break; } } if (!contains) foundEdgeTriggerEvents.Add(foundTrigger); } // search for lines, being connected to an edge of the group foreach (eventChannelLine ecl in eventChannelLinesList) { if (ecl.Line.Visibility == System.Windows.Visibility.Visible && ecl.ListenerComponentId == ec.targets.target.component.id && ecl.TriggerComponentId == ec.sources.source.component.id) { //selectedEventChannelList.AddFirst(ecl); if (!selectedGroupEdgeTriggerEventChannelList.Contains(ecl)) selectedGroupEdgeTriggerEventChannelList.Add(ecl); break; } } // search for each event channel on the edge of the group element } else if (selectedComponentList.Contains(deploymentComponentList[ec.targets.target.component.id]) && !selectedComponentList.Contains(deploymentComponentList[ec.sources.source.component.id])) { foreach (EventListenerPort elp in deploymentComponentList[ec.targets.target.component.id].EventListenerList) { ACS2.eventsTypeEventListenerPortType foundListener = new ACS2.eventsTypeEventListenerPortType(); foundListener.id = ec.targets.target.component.id + "_" + elp.EventListenerId; foundListener.description = elp.EventDescription; bool contains = false; foreach (ACS2.eventsTypeEventListenerPortType etel in foundEdgeListenerEvents) { if (etel.id.Equals(foundListener.id)) { contains = true; break; } } if (!contains) foundEdgeListenerEvents.Add(foundListener); } // search for lines, being connected to an edge of the group foreach (eventChannelLine ecl in eventChannelLinesList) { if (ecl.Line.Visibility == System.Windows.Visibility.Visible && ecl.ListenerComponentId == ec.targets.target.component.id && ecl.TriggerComponentId == ec.sources.source.component.id) { //selectedEventChannelList.AddFirst(ecl); if (!selectedGroupEdgeListenerEventChannelList.Contains(ecl)) selectedGroupEdgeListenerEventChannelList.Add(ecl); break; } } // search for each event channel in the group element } else if (selectedComponentList.Contains(deploymentComponentList[ec.targets.target.component.id]) && selectedComponentList.Contains(deploymentComponentList[ec.sources.source.component.id])) { // search for lines, being between two selected components, but not selected foreach (eventChannelLine ecl in eventChannelLinesList) { if (ecl.Line.Visibility == System.Windows.Visibility.Visible && ecl.ListenerComponentId == ec.targets.target.component.id && ecl.TriggerComponentId == ec.sources.source.component.id) { if (!selectedGroupEventChannelList.Contains(ecl)) selectedGroupEventChannelList.Add(ecl); break; } } } } ArrayList emptyEventChannelLines = new ArrayList(); foreach (eventChannelLine ecl in eventChannelLinesList) { // only check eventchannelLine that correspond to group components bool found = false; foreach (eventChannel ech in eventChannelList) { string source = ech.sources.source.component.id; string target = ech.targets.target.component.id; if (ecl.ListenerComponentId.Equals(target) && ecl.TriggerComponentId.Equals(source)) { found = true; break; } } if (!found) emptyEventChannelLines.Add(ecl); } foreach (eventChannelLine ecl in emptyEventChannelLines) { DeleteEventChannelCommand(ecl); } int eventCount = foundEdgeTriggerEvents.Count + foundEdgeListenerEvents.Count; if (eventCount > 0) { newGroupForBundle.events = new object[eventCount]; foundEdgeListenerEvents.CopyTo(newGroupForBundle.events, 0); foundEdgeTriggerEvents.CopyTo(newGroupForBundle.events, foundEdgeListenerEvents.Count); } // adding the final "new" model to the list of all components (bundles) newGroupForBundle.ports = new object[newGroupForBundle.PortsList.Values.Count]; newGroupForBundle.PortsList.Values.CopyTo(newGroupForBundle.ports, 0); newGroupForBundle.PortsList.Clear(); newGroupForBundle.ComponentCanvas.Children.Clear(); foreach (componentType ct in selectedComponentList) { if (!componentList.ContainsKey(ct.id)) continue; ACS2.componentTypesComponentType ctct = (ACS2.componentTypesComponentType) componentList[ct.id]; if (ctct.singleton) { newGroupForBundle.singleton = true; break; } } if (idForGroup != null && idForGroup != "") newGroupForBundle.InitGraphPorts(idForGroup); else newGroupForBundle.InitGraphPorts(suggestID); // generate the id of the group in the acs string compName = suggestID; counter = 0; if (idForGroup == "" || idForGroup == null) { do { counter++; compName = suggestID + "." + counter; compName = TrimComponentName(compName); } while (deploymentComponentList.ContainsKey(compName)); } else { compName = idForGroup; } BrushConverter bc = new BrushConverter(); if (idForGroup != null && idForGroup != "") { if (componentList.ContainsKey(idForGroup)) componentList.Remove(idForGroup); componentList.Add(idForGroup, newGroupForBundle); AddComponent(idForGroup, true,false,false); } else { if (componentList.ContainsKey(suggestID)) componentList.Remove(suggestID); componentList.Add(suggestID, newGroupForBundle); AddComponent(suggestID, false, false,false); } // find the id of the just added group componentType componentAsGroupElement = null; string searchName; if (idForGroup == "" || idForGroup == null) searchName = suggestID; else searchName = idForGroup; ArrayList longestNameComp = new ArrayList(); componentType longestComp = null; foreach (componentType mc in deploymentComponentList.Values) { if (mc.id.StartsWith(searchName)) longestNameComp.Add(mc); } if (longestNameComp.Count == 1) longestComp = (componentType) longestNameComp[0]; else if (longestNameComp.Count > 1) { foreach (componentType ct in longestNameComp) { if (longestComp == null) longestComp = ct; else if (longestComp.id.Length < ct.id.Length) longestComp = ct; } } if (longestComp != null) { newGroup.GroupID = longestComp.type_id; newGroup.ID = longestComp.id; componentAsGroupElement = longestComp; groupsList.Add(newGroup.ID, newGroup); MoveComponent(longestComp, lowestX + (highestX - lowestX) / 2, lowestY + (highestY - lowestY) / 2); String groupColor = ini.IniReadValue("Layout", "groupcolor"); if (groupColor.Equals("")) groupColor = ACS.LayoutConstants.GROUPRECTANGLECOLOR; longestComp.TopRectangle.Fill = (Brush)bc.ConvertFrom(groupColor); } if (addToUndoStack) { CommandObject co = new CommandObject("Ungroup", componentAsGroupElement); undoStack.Push(co); redoStack.Clear(); } /* * Process Channels where the source becomes a member of a group */ foreach (channel ch in foundEdgeSourceChannels) { outputPortType outPort = null; foreach (object o in componentAsGroupElement.PortsList.Values) { if ((o is outputPortType) && (((outputPortType)o).refs.componentID == ch.source.component.id) && (((outputPortType)o).refs.portID == ch.source.port.id)) { outPort = (outputPortType)o; } } if (outPort == null) continue; /* * add channel with source = newgroup and old target */ channel groupChannel = new channel(); groupChannel.id = NewIdForGroupChannel(); groupChannel.source.component.id = outPort.ComponentId; groupChannel.source.port.id = ch.source.component.id + "_" + ch.source.port.id; groupChannel.target.component.id = ch.target.component.id; groupChannel.target.port.id = ch.target.port.id; if (!ChannelExists(groupChannel)) AddChannel(groupChannel); groupChannel.Line.Y1 = 100; groupChannel.Line.X1 = 100; groupChannel.Line.Y1 = Canvas.GetTop(((outputPortType)(deploymentComponentList[groupChannel.source.component.id]).PortsList[groupChannel.source.port.id]).PortRectangle) + Canvas.GetTop((deploymentComponentList[groupChannel.source.component.id]).ComponentCanvas) + 5; groupChannel.Line.X1 = Canvas.GetLeft(((outputPortType)(deploymentComponentList[groupChannel.source.component.id]).PortsList[groupChannel.source.port.id]).PortRectangle) + Canvas.GetLeft((deploymentComponentList[groupChannel.source.component.id]).ComponentCanvas) + 20; groupChannel.Line.Y2 = Canvas.GetTop(((inputPortType)(deploymentComponentList[ch.target.component.id]).PortsList[ch.target.port.id]).PortRectangle) + Canvas.GetTop((deploymentComponentList[ch.target.component.id]).ComponentCanvas) + 5; groupChannel.Line.X2 = Canvas.GetLeft(((inputPortType)(deploymentComponentList[ch.target.component.id]).PortsList[ch.target.port.id]).PortRectangle) + Canvas.GetLeft((deploymentComponentList[ch.target.component.id]).ComponentCanvas); Canvas.SetZIndex(groupChannel.Line, Canvas.GetZIndex(groupChannel.Line) + 1000); /* * add channel with source = newgroup and old target */ if (ch.GroupOriginalTarget == null) continue; /* * add channel with source = newgroup and targets group original */ channel groupChannel1 = new channel(); groupChannel1.id = NewIdForGroupChannel(); groupChannel1.source.component.id = outPort.ComponentId; groupChannel1.source.port.id = ch.source.component.id + "_" + ch.source.port.id; groupChannel1.target.component.id = ch.target.component.id; groupChannel1.target.port.id = ch.target.port.id; if (!ChannelExists(groupChannel)) AddChannel(groupChannel1); groupChannel1.Line.Y1 = 100; groupChannel1.Line.X1 = 100; groupChannel1.Line.Y1 = Canvas.GetTop(((outputPortType)(deploymentComponentList[groupChannel1.source.component.id]).PortsList[groupChannel1.source.port.id]).PortRectangle) + Canvas.GetTop((deploymentComponentList[groupChannel1.source.component.id]).ComponentCanvas) + 5; groupChannel1.Line.X1 = Canvas.GetLeft(((outputPortType)(deploymentComponentList[groupChannel1.source.component.id]).PortsList[groupChannel1.source.port.id]).PortRectangle) + Canvas.GetLeft((deploymentComponentList[groupChannel1.source.component.id]).ComponentCanvas) + 20; groupChannel1.Line.Y2 = Canvas.GetTop(((inputPortType)(deploymentComponentList[ch.target.component.id]).PortsList[ch.target.port.id]).PortRectangle) + Canvas.GetTop((deploymentComponentList[ch.target.component.id]).ComponentCanvas) + 5; groupChannel1.Line.X2 = Canvas.GetLeft(((inputPortType)(deploymentComponentList[ch.target.component.id]).PortsList[ch.target.port.id]).PortRectangle) + Canvas.GetLeft((deploymentComponentList[ch.target.component.id]).ComponentCanvas); Canvas.SetZIndex(groupChannel1.Line, Canvas.GetZIndex(groupChannel1.Line) + 1000); } // Sort Portslist /* * Process Channels where the target becomes a member of a group */ foreach (channel ch in foundEdgeTargetChannels) { inputPortType inPort = null; foreach (object o in componentAsGroupElement.PortsList.Values) { if ((o is inputPortType) && (((inputPortType)o).refs.componentID == ch.target.component.id) && (((inputPortType)o).refs.portID == ch.target.port.id)) { inPort = (inputPortType)o; } } if (inPort == null) continue; /* * add channel with source = newgroup and old target */ channel groupChannel = new channel(); groupChannel.id = NewIdForGroupChannel(); groupChannel.source.component.id = ch.source.component.id; groupChannel.source.port.id = ch.source.port.id; groupChannel.target.component.id = inPort.ComponentId; groupChannel.target.port.id = ch.target.component.id + "_" + ch.target.port.id; if (!ChannelExists(groupChannel)) AddChannel(groupChannel); groupChannel.Line.Y1 = 100; groupChannel.Line.X1 = 100; groupChannel.Line.Y1 = Canvas.GetTop(((outputPortType)(deploymentComponentList[ch.source.component.id]).PortsList[ch.source.port.id]).PortRectangle) + Canvas.GetTop((deploymentComponentList[ch.source.component.id]).ComponentCanvas) + 5; groupChannel.Line.X1 = Canvas.GetLeft(((outputPortType)(deploymentComponentList[ch.source.component.id]).PortsList[ch.source.port.id]).PortRectangle) + Canvas.GetLeft((deploymentComponentList[ch.source.component.id]).ComponentCanvas) + 20; groupChannel.Line.Y2 = Canvas.GetTop(((inputPortType)(deploymentComponentList[groupChannel.target.component.id]).PortsList[groupChannel.target.port.id]).PortRectangle) + Canvas.GetTop((deploymentComponentList[groupChannel.target.component.id]).ComponentCanvas) + 5; groupChannel.Line.X2 = Canvas.GetLeft(((inputPortType)(deploymentComponentList[groupChannel.target.component.id]).PortsList[groupChannel.target.port.id]).PortRectangle) + Canvas.GetLeft((deploymentComponentList[groupChannel.target.component.id]).ComponentCanvas); Canvas.SetZIndex(groupChannel.Line, Canvas.GetZIndex(groupChannel.Line) + 1000); /* * add channel with source = newgroup and old target */ if (ch.GroupOriginalSource == null) continue; /* * add channel with source = newgroup and targets group original */ channel groupChannel1 = new channel(); groupChannel1.id = NewIdForGroupChannel(); groupChannel1.source.component.id = ch.source.component.id; groupChannel1.source.port.id = ch.source.port.id; groupChannel1.target.component.id = inPort.ComponentId; groupChannel1.target.port.id = ch.target.component.id + "_" + ch.target.port.id; if (!ChannelExists(groupChannel)) AddChannel(groupChannel1); groupChannel1.Line.Y1 = Canvas.GetTop(((outputPortType)(deploymentComponentList[ch.source.component.id]).PortsList[ch.source.port.id]).PortRectangle) + Canvas.GetTop((deploymentComponentList[ch.source.component.id]).ComponentCanvas) + 5; groupChannel1.Line.X1 = Canvas.GetLeft(((outputPortType)(deploymentComponentList[ch.source.component.id]).PortsList[ch.source.port.id]).PortRectangle) + Canvas.GetLeft((deploymentComponentList[ch.source.component.id]).ComponentCanvas); groupChannel1.Line.Y2 = Canvas.GetTop(((inputPortType)(deploymentComponentList[groupChannel1.target.component.id]).PortsList[groupChannel1.target.port.id]).PortRectangle) + Canvas.GetTop((deploymentComponentList[groupChannel1.target.component.id]).ComponentCanvas) + 5; groupChannel1.Line.X2 = Canvas.GetLeft(((inputPortType)(deploymentComponentList[groupChannel1.target.component.id]).PortsList[groupChannel1.target.port.id]).PortRectangle) + Canvas.GetLeft((deploymentComponentList[groupChannel1.target.component.id]).ComponentCanvas) + 20; Canvas.SetZIndex(groupChannel1.Line, Canvas.GetZIndex(groupChannel1.Line) + 1000); } // hide the eventchannels within a group foreach (eventChannelLine ecl in selectedGroupEventChannelList) { ecl.Line.Visibility = System.Windows.Visibility.Hidden; newGroup.AddedEventChannelsList.AddLast(ecl); } // hide all eventchannels where the group is a listener foreach (eventChannelLine ecl in selectedGroupEdgeListenerEventChannelList) { ecl.Line.Visibility = System.Windows.Visibility.Hidden; newGroup.AddedEventChannelsList.AddLast(ecl); } // hide all eventchannels where the group is a trigger foreach (eventChannelLine ecl in selectedGroupEdgeTriggerEventChannelList) { ecl.Line.Visibility = System.Windows.Visibility.Hidden; newGroup.AddedEventChannelsList.AddLast(ecl); } // Targets foreach (eventChannelLine ecl in selectedGroupEdgeListenerEventChannelList) { List<eventChannel> ecList = GetEventChannelsFromLine(ecl); foreach (eventChannel ec in ecList) { string targetEvent = ec.targets.target.component.id + "_" + ec.targets.target.eventPort.id; if (eventChannelExists(compName, targetEvent, ecl.TriggerComponentId, ec.sources.source.eventPort.id)) continue; eventChannel tmpEC = new eventChannel(); tmpEC.sources.source.component.id = ecl.TriggerComponentId; tmpEC.sources.source.eventPort.id = ec.sources.source.eventPort.id; tmpEC.targets.target.component.id = compName; tmpEC.targets.target.eventPort.id = targetEvent; tmpEC.id = compName + "_" + ecl.TriggerComponentId + "_" + tmpEC.sources.source.eventPort.id + "_" + tmpEC.targets.target.eventPort.id; tmpEC.GroupOriginalTarget = ec.targets.target; if (EventChannelHasGroupSource(ec)) tmpEC.GroupOriginalSource = ec.GroupOriginalSource; eventChannelList.Add(tmpEC); } if (eventChannelLineExists(compName, ecl.TriggerComponentId)) continue; eventChannelLine groupEC = new eventChannelLine(); double x = lowestX + (highestX - lowestX) / 2; double y = lowestY + (highestY - lowestY) / 2; groupEC.Line.X1 = ecl.Line.X1; groupEC.Line.Y1 = ecl.Line.Y1; groupEC.Line.X2 = x + componentAsGroupElement.ComponentCanvas.Width / 2 - 18; groupEC.Line.Y2 = y + componentAsGroupElement.ComponentCanvas.Height - 4; Canvas.SetZIndex(groupEC.Line, -1001); groupEC.TriggerComponentId = ecl.TriggerComponentId; groupEC.ListenerComponentId = compName; groupEC.HasGroupTarget = true; groupEC.HasGroupSource = EventChannelLineHasGroupSource(ecl); AddEventChannelCommand(groupEC, false); canvas.Children.Add(groupEC.Line); } // Sources foreach (eventChannelLine ecl in selectedGroupEdgeTriggerEventChannelList) { //Copy eventChannels List<eventChannel> ecList = GetEventChannelsFromLine(ecl); foreach (eventChannel ec in ecList) { eventChannel tmpEC = new eventChannel(); Console.WriteLine("compName"); tmpEC.sources.source.component.id = compName; tmpEC.sources.source.eventPort.id = ec.sources.source.component.id + "_" + ec.sources.source.eventPort.id; tmpEC.targets.target.component.id = ecl.ListenerComponentId; tmpEC.targets.target.eventPort.id = ec.targets.target.eventPort.id; tmpEC.id = compName + "_" + tmpEC.sources.source.eventPort.id + "_" + tmpEC.targets.target.eventPort.id; tmpEC.GroupOriginalSource = ec.sources.source; if (EventChannelHasGroupTarget(ec)) tmpEC.GroupOriginalTarget = ec.GroupOriginalTarget; eventChannelList.Add(tmpEC); } if (eventChannelLineExists(ecl.ListenerComponentId, compName)) continue; // Add EventchannelLine eventChannelLine groupEC = new eventChannelLine(); double x = lowestX + (highestX - lowestX) / 2; double y = lowestY + (highestY - lowestY) / 2; groupEC.Line.X1 = x + componentAsGroupElement.ComponentCanvas.Width / 2 + 18; groupEC.Line.Y1 = y + componentAsGroupElement.ComponentCanvas.Height - 4; groupEC.Line.X2 = ecl.Line.X2; groupEC.Line.Y2 = ecl.Line.Y2; Canvas.SetZIndex(groupEC.Line, -1001); groupEC.TriggerComponentId = compName; groupEC.ListenerComponentId = ecl.ListenerComponentId; groupEC.HasGroupSource = true; groupEC.HasGroupTarget = EventChannelLineHasGroupTarget(ecl); AddEventChannelCommand(groupEC, false); canvas.Children.Add(groupEC.Line); } DeleteDanglingChannels(); HideGroupChannels(); // Delete all Eventchannels where either the source or the target does not exist anymore DeleteDanglingEventChannelLines(); DeleteDanglingEventChannels(); deploymentModel.eventChannels = (eventChannel[])eventChannelList.ToArray(typeof(eventChannel)); // store the group in the deployment model if (storeGroup) { group[] tempGroups = deploymentModel.groups; if (tempGroups == null) { tempGroups = new group[1]; } else { Array.Resize(ref tempGroups, deploymentModel.groups.Count() + 1); } deploymentModel.groups = tempGroups; group groupForDeployment = new group(); groupForDeployment.id = compName; groupForDeployment.componentId = new string[selectedGroupComponentList.Count]; for (int i = 0; i < selectedGroupComponentList.Count; i++) { groupForDeployment.componentId[i] = ((componentType)selectedGroupComponentList[i]).id; } deploymentModel.groups[deploymentModel.groups.Count() - 1] = groupForDeployment; } ClearSelectedComponentList(); ClearSelectedChannelList(); ClearSelectedEventChannelList(); //AddSelectedComponent(deploymentComponentList[compName]); Console.WriteLine("Compname is:" + compName); return compName; }
/// <summary> /// Save the selected group to a file, so that it can be reused /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void SaveGroupButton_Click(object sender, RoutedEventArgs e) { groupComponent groupToSave = null; foreach (componentType mc in selectedComponentList) { if (mc.ComponentType == ACS2.componentTypeDataTypes.group) { groupToSave = groupsList[mc.id]; break; } } if (groupToSave != null) { storageDialog = new StorageDialog(); string[] filesInGroupsFolder; if (ini.IniReadValue("Options", "useAppDataFolder").Equals("true")) { filesInGroupsFolder = Directory.GetFiles(Environment.GetFolderPath(System.Environment.SpecialFolder.ApplicationData) + "\\AsTeRICS\\ACS\\groups\\", "*.agr"); } else { filesInGroupsFolder = Directory.GetFiles(AppDomain.CurrentDomain.BaseDirectory + "\\groups\\", "*.agr"); } foreach (string s in filesInGroupsFolder) { storageDialog.filenameListbox.Items.Add(s.Substring(s.LastIndexOf('\\') + 1)); } storageDialog.filenameListbox.SelectionChanged += filenameListbox_SelectionChanged; storageDialog.Title = Properties.Resources.GroupStoreDialogTitle; storageDialog.listLabel.Content = Properties.Resources.GroupStoreDialogListLabel; storageDialog.filenameTextbox.Text = "NewGroup.agr"; storageDialog.modelNameLabel.Content = Properties.Resources.GroupStoreDialogGroupName; storageDialog.Owner = this; storageDialog.ShowDialog(); if (storageDialog.filenameTextbox.Text != null && storageDialog.filenameTextbox.Text != "") { try { model groupModelToSave; if (groupToSave != null) { ClearSelectedChannelList(); ClearSelectedEventChannelList(); ClearSelectedComponentList(); foreach (componentType componentInGroup in groupToSave.AddedComponentList) { AddSelectedComponent(deploymentComponentList[componentInGroup.id]); } // make a submodel, containing all grouging relevant data groupModelToSave = new model(); groupModelToSave.modelName = groupToSave.GroupID; // insert all selected components to the model LinkedList<componentType> t = new LinkedList<componentType>(); for (int i = 0; i < selectedComponentList.Count; i++) { componentType ct = selectedComponentList.ElementAt(i); t.AddLast(ct); } groupModelToSave.components = t.ToArray(); // adding a group element to save the aliases groupModelToSave.groups = new group[1]; foreach (group groupToAdd in deploymentModel.groups) { if (groupToAdd.id == groupToSave.ID) { groupModelToSave.groups[0] = groupToAdd; break; } } //get all selected channels where the source and target components //are also selected LinkedList<channel> copyChannels = new LinkedList<channel>(); foreach (channel c in groupToSave.AddedChannelsList) { bool sourceFound, targetFound; sourceFound = targetFound = false; foreach (componentType mc in groupModelToSave.components) { if (mc.id == c.source.component.id) sourceFound = true; if (mc.id == c.target.component.id) targetFound = true; if (sourceFound && targetFound) break; } if (sourceFound && targetFound) copyChannels.AddLast(c); } // Adding dummy channels to make the input and output ports of the group visible componentType groupComponent = deploymentComponentList[groupToSave.ID]; int index = 0; foreach (object o in groupComponent.ports) { channel c = new channel(); c.id = "bindingveigl." + index; if (o is inputPortType) { c.source.component.id = pasteDummyName; c.source.port.id = "out"; c.target.component.id = ((inputPortType)o).refs.componentID; c.target.port.id = ((inputPortType)o).refs.portID; } else { c.source.component.id = ((outputPortType)o).refs.componentID; c.source.port.id = ((outputPortType)o).refs.portID; c.target.component.id = pasteDummyName; c.target.port.id = "in"; } copyChannels.AddLast(c); index++; } groupModelToSave.channels = new channel[copyChannels.Count]; for (int i = 0; i < copyChannels.Count; i++) groupModelToSave.channels[i] = copyChannels.ElementAt(i); // get all selected Eventchannels index = 0; LinkedList<eventChannel> copyEventChannels = new LinkedList<eventChannel>(); LinkedList<EventListenerPort> foundEdgeListenerEvents = new LinkedList<EventListenerPort>(); LinkedList<EventTriggerPort> foundEdgeTriggerEvents = new LinkedList<EventTriggerPort>(); foreach (eventChannel ec in eventChannelList) { // search for each event channel on the edge of the group element if (!selectedComponentList.Contains(deploymentComponentList[ec.targets.target.component.id]) && selectedComponentList.Contains(deploymentComponentList[ec.sources.source.component.id])) { eventChannel newEc = new eventChannel(); newEc.id = "eventbindingveigl." + index; newEc.sources.source.component.id = ec.sources.source.component.id; newEc.sources.source.eventPort.id = ec.sources.source.eventPort.id; newEc.targets.target.component.id = pasteDummyName; newEc.targets.target.eventPort.id = "eventlistener"; index++; copyEventChannels.AddLast(newEc); // search for each event channel on the edge of the group element } else if (selectedComponentList.Contains(deploymentComponentList[ec.targets.target.component.id]) && !selectedComponentList.Contains(deploymentComponentList[ec.sources.source.component.id])) { eventChannel newEc = new eventChannel(); newEc.id = "eventbindingveigl." + index; newEc.sources.source.component.id = pasteDummyName; newEc.sources.source.eventPort.id = "eventtrigger"; newEc.targets.target.component.id = ec.targets.target.component.id; newEc.targets.target.eventPort.id = ec.targets.target.eventPort.id; index++; copyEventChannels.AddLast(newEc); } else if ((selectedComponentList.Contains(deploymentComponentList[ec.targets.target.component.id]) && selectedComponentList.Contains(deploymentComponentList[ec.sources.source.component.id]))) { copyEventChannels.AddFirst(ec); } } // Adding dummy eventchannels to make the input and output ports of the group visible foreach (EventListenerPort elp in groupComponent. EventListenerList) { eventChannel newEc = new eventChannel(); foreach (componentType mc in groupModelToSave.components) { if (elp.EventListenerId.StartsWith(mc.id)) { newEc.targets.target.component.id = mc.id; newEc.targets.target.eventPort.id = ((EventListenerPort)mc.EventListenerList[0]).EventListenerId; newEc.id = "eventbindingveigl." + index; newEc.sources.source.component.id = pasteDummyName; newEc.sources.source.eventPort.id = "eventtrigger"; index++; copyEventChannels.AddLast(newEc); break; } } } foreach (EventTriggerPort etp in groupComponent.EventTriggerList) { eventChannel newEc = new eventChannel(); foreach (componentType mc in groupModelToSave.components) { if (etp.EventTriggerId.StartsWith(mc.id)) { newEc.id = "eventbindingveigl." + index; newEc.sources.source.component.id = mc.id; newEc.sources.source.eventPort.id = ((EventTriggerPort)mc.EventTriggerList[0]).EventTriggerId; newEc.targets.target.component.id = pasteDummyName; newEc.targets.target.eventPort.id = "eventlistener"; index++; copyEventChannels.AddLast(newEc); break; } } } if (copyEventChannels.Count == 0) { groupModelToSave.eventChannels = null; } else { groupModelToSave.eventChannels = copyEventChannels.ToArray(); } groupModelToSave = CopyModel(groupModelToSave); // write group stream XmlSerializer x = new XmlSerializer(groupModelToSave.GetType()); string filename; if (ini.IniReadValue("Options", "useAppDataFolder").Equals("true")) { filename = Environment.GetFolderPath(System.Environment.SpecialFolder.ApplicationData) + "\\AsTeRICS\\ACS\\groups\\" + storageDialog.filenameTextbox.Text; } else { filename = AppDomain.CurrentDomain.BaseDirectory + "\\groups\\" + storageDialog.filenameTextbox.Text; } if (!filename.EndsWith(".agr")) { filename += ".agr"; } FileStream str = new FileStream(filename, FileMode.Create); x.Serialize(str, groupModelToSave); str.Close(); // add new group to list of groups bool alreadyInMenu = false; foreach (RibbonApplicationSplitMenuItem i in groupDropDown.Items) { if (((string)i.CommandParameter) == filename) { alreadyInMenu = true; break; } } if (!alreadyInMenu) { RibbonApplicationSplitMenuItem i = new RibbonApplicationSplitMenuItem(); string header = filename.Substring(filename.LastIndexOf('\\') + 1); i.Header = header.Substring(0, header.LastIndexOf('.')); i.Click += AddGroupFromRibbonMenu; i.CommandParameter = filename; groupDropDown.Items.Add(i); } } } catch (Exception ex) { MessageBox.Show(Properties.Resources.StoreModelOnAREError, Properties.Resources.GroupStoreErrorHeader, MessageBoxButton.OK, MessageBoxImage.Error); traceSource.TraceEvent(TraceEventType.Error, 3, ex.Message); } } } else { MessageBox.Show(Properties.Resources.GroupStoreNoGroupSelected, Properties.Resources.GroupStoreErrorHeader, MessageBoxButton.OK, MessageBoxImage.Information); } }
/// <summary> /// check if there is already a groupchannel with same source and target /// </summary> /// <param name="groupChannel">channel which existencs should be checked</param> /// <returns></returns> private bool ChannelExists(channel groupChannel) { foreach (channel c in deploymentChannelList.Values) { if (c.source.component.id.Equals(groupChannel.source.component.id) && c.target.component.id.Equals(groupChannel.target.component.id) && c.source.port.id.Equals(groupChannel.source.port.id) && c.target.port.id.Equals(groupChannel.target.port.id)) return true; } return false; }
/// <summary> /// Copy alle Components of the copyModel to the actual model /// </summary> private void PasteCopiedModel(model modelToPaste, bool namesAreValid, bool addToUndoStack) { CommandObject co = new CommandObject("Delete"); if (modelToPaste == null) return; // loading the components /* * Create a list of lists which contain all elements which should be within a group * after the paste method finishes */ ArrayList groupComps = new ArrayList(); ArrayList groups = new ArrayList(); ArrayList groupNames = new ArrayList(); foreach (componentType ct in modelToPaste.components) { if (ct.ComponentType != ACS2.componentTypeDataTypes.group) continue; groups.Add(ct); groupComponent gc = groupsList[ct.id]; ArrayList groupElems = new ArrayList(); foreach (componentType child in gc.AddedComponentList) { foreach (componentType child1 in modelToPaste.components) { if (child1.id.Equals(child.id)) { groupElems.Add(child1); } } } if (groupElems.Count > 0) { groupComps.Add(groupElems); bool namevalid = namesAreValid; int i = 1; while (namevalid == false) { string modelID = ct.id + "." + i; if (!deploymentComponentList.ContainsKey(modelID)) { namevalid = true; groupNames.Add(modelID); } else i++; } } } // Rename components and update all channels Dictionary<string, string> changedComponents = new Dictionary<string, string>(); foreach (object o in modelToPaste.components) { componentType modelComp = (componentType)o; if (modelComp.ComponentType == ACS2.componentTypeDataTypes.group) continue; // change id bool namevalid = namesAreValid; int i = 1; while (namevalid == false) { string modelID = modelComp.id + "." + i; if (!deploymentComponentList.ContainsKey(modelID)) { if (modelToPaste.channels != null) { foreach (channel c in modelToPaste.channels) { if (c.source.component.id == modelComp.id) c.source.component.id = modelID; if (c.target.component.id == modelComp.id) c.target.component.id = modelID; } } if (modelToPaste.eventChannels != null) { foreach (eventChannel ec in modelToPaste.eventChannels) { if (ec.sources.source.component.id == modelComp.id) ec.sources.source.component.id = modelID; if (ec.targets.target.component.id == modelComp.id) ec.targets.target.component.id = modelID; } } changedComponents.Add(modelComp.id,modelID); modelComp.id = modelID; namevalid = true; } else i++; } // check, if bundle is available if (componentList.ContainsKey(modelComp.type_id)) { // init the ArrayLists containing the ports. Used for easier and faster access modelComp.InitArrayLists(); foreach (propertyType p in modelComp.properties) { modelComp.PropertyArrayList.Add(p); } // copy the property datatype and description from bundle_description // also copy the port datatypes form the bundle_description // works only, if bundle and deployment fits to each other try { // search for bundle component Asterics.ACS2.componentTypesComponentType bundleComponent = (Asterics.ACS2.componentTypesComponentType)componentList[modelComp.type_id]; // copy the ComponentType of the component modelComp.ComponentType = bundleComponent.type.Value; if (modelComp.properties != null) { foreach (propertyType deploymentProperty in modelComp.properties) { int index = 0; // searching for the right component property while (deploymentProperty.name != bundleComponent.properties[index].name) { index++; } // copy the properties of the component deploymentProperty.DataType = bundleComponent.properties[index].type; // check, if the property is a dynamic property if (bundleComponent.properties[index].getStringList) { deploymentProperty.GetStringList = true; } else { deploymentProperty.GetStringList = false; } // check the value fitting to the datatype if (!CheckPropertyDatatype(deploymentProperty.value, deploymentProperty.DataType)) { throw new LoadPropertiesException(); } deploymentProperty.Description = bundleComponent.properties[index].description; if (bundleComponent.properties[index].combobox != null) { deploymentProperty.ComboBoxStrings = bundleComponent.properties[index].combobox.Split(new String[] { "//" }, StringSplitOptions.None); } deploymentProperty.PropertyChanged += ComponentPropertyChanged; deploymentProperty.PropertyChangeError += ComponentPropertyChangeError; } // check the amount of properties. Cause an exception, if the bundle has more properties then the deployment if ((bundleComponent.properties == null) && (modelComp.properties.Length != 0)) { throw new LoadPropertiesException(); } else if ((bundleComponent.properties != null) && (modelComp.properties.Length != bundleComponent.properties.Length)) { throw new LoadPropertiesException(); } } foreach (object portObj in modelComp.PortsList.Values) { // searching for the inPorts if (portObj is inputPortType) { int index = 0; inputPortType deploymentInPort = (inputPortType)portObj; ArrayList helperListInPort = new ArrayList(); // a list with all InPorts of a component for the bundel_description foreach (object bundleInPort in bundleComponent.ports) { if (bundleInPort is ACS2.inputPortType) { helperListInPort.Add(bundleInPort); } } while (deploymentInPort.portTypeID != ((ACS2.inputPortType)helperListInPort[index]).id) { index++; // searching for the right input port } // copy the dataType of the port deploymentInPort.PortDataType = ((Asterics.ACS2.inputPortType)helperListInPort[index]).dataType; deploymentInPort.MustBeConnected = ((Asterics.ACS2.inputPortType)helperListInPort[index]).mustBeConnected; deploymentInPort.Description = ((Asterics.ACS2.inputPortType)helperListInPort[index]).description; deploymentInPort.ComponentId = ((Asterics.ACS2.inputPortType)helperListInPort[index]).ComponentId; deploymentInPort.ComponentTypeId = ((Asterics.ACS2.inputPortType)helperListInPort[index]).id; // update the alias for group ports via property changed listener deploymentInPort.PropertyChanged += InputPortIntPropertyChanged; ACS2.propertyType[] sourceProperties = ((Asterics.ACS2.inputPortType)helperListInPort[index]).properties; if ((sourceProperties != null) && (sourceProperties.Length > 0)) { //if (deploymentInPort.PropertyArrayList.Count > 0) { foreach (propertyType deploymentProperty in deploymentInPort.properties) { int inPortIndex = 0; while (deploymentProperty.name != sourceProperties[inPortIndex].name) { inPortIndex++; } // copy the properties of the inPort deploymentProperty.DataType = sourceProperties[inPortIndex].type; deploymentProperty.Description = sourceProperties[inPortIndex].description; if (sourceProperties[inPortIndex].combobox != null) { deploymentProperty.ComboBoxStrings = sourceProperties[inPortIndex].combobox.Split(new String[] { "//" }, StringSplitOptions.None); } deploymentProperty.PropertyChanged += InPortPropertyChanged; deploymentProperty.PropertyChangeError += ComponentPropertyChangeError; } // check the amount of properties. Cause an exception, if the bundle has more properties then the deployment if (deploymentInPort.properties.Length != sourceProperties.Length) { throw new Exception(); } } deploymentInPort.properties = (propertyType[])deploymentInPort.PropertyArrayList.ToArray(typeof(propertyType)); } else { // comparing all outPports int index = 0; outputPortType outPort = (outputPortType)portObj; ArrayList helperListOutPort = new ArrayList(); foreach (object origOutPort in bundleComponent.ports) { if (origOutPort is ACS2.outputPortType) { helperListOutPort.Add(origOutPort); } } while (outPort.portTypeID != ((Asterics.ACS2.outputPortType)helperListOutPort[index]).id) { index++; } // copy the dataType of the port outPort.PortDataType = ((Asterics.ACS2.outputPortType)helperListOutPort[index]).dataType; outPort.Description = ((Asterics.ACS2.outputPortType)helperListOutPort[index]).description; outPort.ComponentId = ((Asterics.ACS2.outputPortType)helperListOutPort[index]).ComponentId; outPort.ComponentTypeId = ((Asterics.ACS2.outputPortType)helperListOutPort[index]).id; // update the alias for group ports via property changed listener outPort.PropertyChanged += OutputPortIntPropertyChanged; ACS2.propertyType[] sourceProperties = ((Asterics.ACS2.outputPortType)helperListOutPort[index]).properties; if ((sourceProperties != null) && (sourceProperties.Length > 0)) { //if (outPort.PropertyArrayList.Count > 0) { foreach (propertyType compProperty in outPort.properties) { int outPortIndex = 0; while (compProperty.name != sourceProperties[outPortIndex].name) { outPortIndex++; } // copy the properties of the outPort compProperty.DataType = sourceProperties[outPortIndex].type; compProperty.Description = sourceProperties[outPortIndex].description; if (sourceProperties[outPortIndex].combobox != null) { compProperty.ComboBoxStrings = sourceProperties[outPortIndex].combobox.Split(new String[] { "//" }, StringSplitOptions.None); } compProperty.PropertyChanged += OutPortPropertyChanged; compProperty.PropertyChangeError += ComponentPropertyChangeError; } // check the amount of properties. Cause an exception, if the bundle has more properties then the deployment if (outPort.properties.Length != sourceProperties.Length) { throw new Exception(); } } outPort.properties = (propertyType[])outPort.PropertyArrayList.ToArray(typeof(propertyType)); } } } catch (Exception ex) { MessageBox.Show(Properties.Resources.CopyPropertiesErrorTextFormat(modelComp.id), Properties.Resources.CopyPropertiesErrorHeader, MessageBoxButton.OK, MessageBoxImage.Error); traceSource.TraceEvent(TraceEventType.Error, 3, ex.Message); //versionconflict int posX; int posY; // set coordinates for the component in case there are not already set if ((modelComp.layout.posX == null) || (modelComp.layout.posX == "") || (modelComp.layout.posY == null) || (modelComp.layout.posY == "")) { posX = 40; posY = 40; } else { posX = Int32.Parse(modelComp.layout.posX); posY = Int32.Parse(modelComp.layout.posY); } // backup component to load properties componentType backupComp = modelComp; modelComp = componentType.CopyFromBundleModel((Asterics.ACS2.componentTypesComponentType)componentList[modelComp.type_id], modelComp.id); modelComp.layout.posX = Convert.ToString(posX); modelComp.layout.posY = Convert.ToString(posY); // HasVersionConflict indicates a version conflict between the component in a stored model and // the component in the bundle descriptor modelComp.HasVersionConflict = true; modelComp.ComponentCanvas.Background = new SolidColorBrush(Colors.Orange); //break; // new code, copy property values from invalid (version conflict) component foreach (propertyType deploymentProperty in modelComp.properties) { foreach (propertyType backupProperty in backupComp.properties) { if (deploymentProperty.name == backupProperty.name) { if (CheckPropertyDatatype(backupProperty.value, deploymentProperty.DataType)) { deploymentProperty.value = backupProperty.value; // try-parse is missing } break; } } } } // end of exception // set coordinates for the component in case there are not already set if ((modelComp.layout.posX == null) || (modelComp.layout.posX == "") || (modelComp.layout.posY == null) || (modelComp.layout.posY == "")) { int[] pos = ProperComponentCoordinates(40, 40); modelComp.layout.posX = Convert.ToString(pos[0]); modelComp.layout.posY = Convert.ToString(pos[1]); } // Searching for the event triggers and event listeners of a component Asterics.ACS2.componentTypesComponentType bundleComponentEvents = (Asterics.ACS2.componentTypesComponentType)componentList[modelComp.type_id]; // If component has version conflict, the events are already set by 'CopyFromBundleModel' if ((bundleComponentEvents.events != null) && (bundleComponentEvents.events != null) && !modelComp.HasVersionConflict) { foreach (object eventO in bundleComponentEvents.events) { if (eventO is ACS2.eventsTypeEventListenerPortType) { ACS2.eventsTypeEventListenerPortType compEl = (ACS2.eventsTypeEventListenerPortType)eventO; EventListenerPort el = new EventListenerPort(); el.EventListenerId = compEl.id; el.ComponentId = modelComp.id; el.EventDescription = compEl.description; modelComp.EventListenerList.Add(el); } else if (eventO is ACS2.eventsTypeEventTriggererPortType) { ACS2.eventsTypeEventTriggererPortType compEl = (ACS2.eventsTypeEventTriggererPortType)eventO; EventTriggerPort el = new EventTriggerPort(); el.EventTriggerId = compEl.id; el.ComponentId = modelComp.id; el.EventDescription = compEl.description; modelComp.EventTriggerList.Add(el); } } } // if the component has no version conflict, it will be pasted on the layout, otherwise, it is already on the // canvas (done by 'CopyFromBundleModel') if (!modelComp.HasVersionConflict) { modelComp.InitGraphLayout(modelComp.id); } else { //deploymentModel.components = deploymentComponentList.Values.ToArray(); } canvas.Children.Add(modelComp.ComponentCanvas); KeyboardNavigation.SetTabIndex(modelComp.ComponentCanvas, canvas.Children.Count + 1); modelComp.Label.Text = modelComp.id; double positionX = (Int32.Parse(modelComp.layout.posX) + copyXOffset * copyOffsetMulti); if (positionX + modelComp.ComponentCanvas.Width > canvas.RenderSize.Width) positionX = canvas.RenderSize.Width - modelComp.ComponentCanvas.Width; double positionY = (Int32.Parse(modelComp.layout.posY) + copyYOffset * copyOffsetMulti); if (positionY + modelComp.ComponentCanvas.Height > canvas.RenderSize.Height) positionY = canvas.RenderSize.Height - modelComp.ComponentCanvas.Height; modelComp.layout.posX = positionX.ToString(); modelComp.layout.posY = positionY.ToString(); deploymentComponentList.Add(modelComp.id, modelComp); //componentList.Add(modelComp.id, modelComp); // adding context menu modelComp.MainRectangle.ContextMenu = componentContextMenu; // adding keyboard focus listener modelComp.ComponentCanvas.KeyDown += Component_KeyDown; modelComp.ComponentCanvas.KeyUp += Component_KeyUp; modelComp.ComponentCanvas.Focusable = true; modelComp.ComponentCanvas.GotKeyboardFocus += ComponentCanvas_GotKeyboardFocus; modelComp.ComponentCanvas.LostKeyboardFocus += ComponentCanvas_LostKeyboardFocus; // adding property changed listener modelComp.PropertyChanged += ComponentIntPropertyChanged; modelComp.TopGrid.ContextMenu = componentContextMenu; modelComp.TopRectangle.ContextMenu = componentContextMenu; // set position of component on the canvas Canvas.SetLeft(modelComp.ComponentCanvas, Int32.Parse(modelComp.layout.posX)); Canvas.SetTop(modelComp.ComponentCanvas, Int32.Parse(modelComp.layout.posY)); // Adapt the size of MainRectangle, if more then MAINRECTANGLENUMBEROFPORTS are in a component int numInPorts = 0; int numOutPorts = 0; foreach (object objPort in modelComp.PortsList.Values) { if (objPort is inputPortType) { numInPorts++; } else { numOutPorts++; } } if (numOutPorts > ACS.LayoutConstants.MAINRECTANGLENUMBEROFPORTS) { modelComp.MainRectangle.Height += (numOutPorts - ACS.LayoutConstants.MAINRECTANGLENUMBEROFPORTS) * (ACS.LayoutConstants.OUTPORTDISTANCE); modelComp.ComponentCanvas.Height += (numOutPorts - ACS.LayoutConstants.MAINRECTANGLENUMBEROFPORTS) * (ACS.LayoutConstants.OUTPORTDISTANCE); } else if (numInPorts > ACS.LayoutConstants.MAINRECTANGLENUMBEROFPORTS) { modelComp.MainRectangle.Height += (numInPorts - ACS.LayoutConstants.MAINRECTANGLENUMBEROFPORTS) * (ACS.LayoutConstants.INPORTDISTANCE); modelComp.ComponentCanvas.Height += (numInPorts - ACS.LayoutConstants.MAINRECTANGLENUMBEROFPORTS) * (ACS.LayoutConstants.INPORTDISTANCE); } // Adapt the position of event trigger and event listener port, if the component has more input/output ports if (modelComp.EventListenerList.Count > 0) { Canvas.SetTop(modelComp.EventListenerPolygon.InputEventPortCanvas, modelComp.MainRectangle.Height + ACS.LayoutConstants.MAINRECTANGLEOFFSETY - 10); } if (modelComp.EventTriggerList.Count > 0) { Canvas.SetTop(modelComp.EventTriggerPolygon.OutputEventPortCanvas, modelComp.MainRectangle.Height + ACS.LayoutConstants.MAINRECTANGLEOFFSETY - 10); } } else { MessageBox.Show(Properties.Resources.LoadComponentNotFoundFormat(modelComp.type_id), Properties.Resources.CopyPropertiesErrorHeader, MessageBoxButton.OK, MessageBoxImage.Error); } // check, if component has a gui component, and load the gui component if (modelComp.gui != null) { AddGUIComponent(modelComp); } } deploymentModel.components = deploymentComponentList.Values.ToArray(); // loading the channels if (modelToPaste.channels != null) { foreach (object o in modelToPaste.channels) { channel modChannel = (channel)o; // check versionconflict: add only channels to components without a conflict if ((deploymentComponentList.ContainsKey(modChannel.source.component.id)) && (deploymentComponentList.ContainsKey(modChannel.target.component.id))) { // one of the channels component has a conflict. Check, if port is available and datatype fits together componentType tempCompOut = (componentType)deploymentComponentList[modChannel.source.component.id]; componentType tempCompIn = (componentType)deploymentComponentList[modChannel.target.component.id]; // try, if the ports are still available if ((tempCompOut.PortsList.Contains(modChannel.source.port.id)) && (tempCompIn.PortsList.Contains(modChannel.target.port.id))) { // check the datatypes of the ports, for the case, that they have been changed //if (CheckInteroperabilityOfPorts(((outputPortType)tempCompOut.PortsList[modChannel.source.port.id]).PortDataType, ((inputPortType)tempCompIn.PortsList[modChannel.target.port.id]).PortDataType)) { modChannel.id = NewIdForChannel(); AddChannel(modChannel); modChannel.Line.Y1 = Canvas.GetTop(((outputPortType)tempCompOut.PortsList[modChannel.source.port.id]).PortRectangle) + Canvas.GetTop(tempCompOut.ComponentCanvas) + 5; modChannel.Line.X1 = Canvas.GetLeft(((outputPortType)tempCompOut.PortsList[modChannel.source.port.id]).PortRectangle) + Canvas.GetLeft(tempCompOut.ComponentCanvas) + 20; modChannel.Line.Y2 = Canvas.GetTop(((inputPortType)tempCompIn.PortsList[modChannel.target.port.id]).PortRectangle) + Canvas.GetTop(tempCompIn.ComponentCanvas) + 5; modChannel.Line.X2 = Canvas.GetLeft(((inputPortType)tempCompIn.PortsList[modChannel.target.port.id]).PortRectangle) + Canvas.GetLeft(tempCompIn.ComponentCanvas); Canvas.SetZIndex(modChannel.Line, Canvas.GetZIndex(modChannel.Line) + 1000); //} //else { // // if no event listener Port can be found, the component has a version conflict // MessageBox.Show(Properties.Resources.CopyChannelsErrorTextFormat(tempCompOut.id, tempCompIn.id), Properties.Resources.CopyChannelsErrorHeader, MessageBoxButton.OK, MessageBoxImage.Error); // tempCompIn.ComponentCanvas.Background = new SolidColorBrush(Colors.Red); // tempCompIn.HasVersionConflict = true; // tempCompOut.ComponentCanvas.Background = new SolidColorBrush(Colors.Red); // tempCompOut.HasVersionConflict = true; //} } else { if (!tempCompOut.PortsList.Contains(modChannel.source.port.id)) { MessageBox.Show(Properties.Resources.CopyChannelErrorNotFoundFormat(tempCompOut.id, tempCompIn.id, modChannel.source.port.id), Properties.Resources.CopyChannelsErrorHeader, MessageBoxButton.OK, MessageBoxImage.Error); tempCompOut.ComponentCanvas.Background = new SolidColorBrush(Colors.Orange); tempCompOut.HasVersionConflict = true; } else { MessageBox.Show(Properties.Resources.CopyChannelErrorNotFoundFormat(tempCompOut.id, tempCompIn.id, modChannel.source.port.id), Properties.Resources.CopyChannelsErrorHeader, MessageBoxButton.OK, MessageBoxImage.Error); tempCompIn.ComponentCanvas.Background = new SolidColorBrush(Colors.Orange); tempCompIn.HasVersionConflict = true; } } } } } // Loading the events and drawing the lines between the event ports if (modelToPaste.eventChannels != null) { bool foundLine = false; foreach (object o in modelToPaste.eventChannels) { eventChannel evChannel = (eventChannel)o; bool foundTriggerPort = false; bool foundListenerPort = false; try { foreach (EventTriggerPort checkEvent in ((componentType)deploymentComponentList[evChannel.sources.source.component.id]).EventTriggerList) { if (checkEvent.ComponentId == evChannel.sources.source.component.id && checkEvent.EventTriggerId == evChannel.sources.source.eventPort.id) { foundTriggerPort = true; break; } } if (foundTriggerPort) { foreach (EventListenerPort checkEvent in ((componentType)deploymentComponentList[evChannel.targets.target.component.id]).EventListenerList) { if (checkEvent.ComponentId == evChannel.targets.target.component.id && checkEvent.EventListenerId == evChannel.targets.target.eventPort.id) { foundListenerPort = true; break; } } if (foundListenerPort) { foreach (eventChannelLine channelLine in eventChannelLinesList) { if ((evChannel.sources.source.component.id == channelLine.TriggerComponentId) && (evChannel.targets.target.component.id == channelLine.ListenerComponentId)) { foundLine = true; break; } } if (!foundLine) { eventChannelLine eCL = new eventChannelLine(); eCL.Line.X1 = Canvas.GetLeft(((componentType)deploymentComponentList[evChannel.sources.source.component.id]).ComponentCanvas) + LayoutConstants.EVENTOUTPORTCANVASOFFSETX + LayoutConstants.EVENTPORTWIDTH / 2 + 5; //eCL.Line.Y1 = Canvas.GetTop(((modelComponent)deploymentComponentList[evChannel.sources.source.component.id]).ComponentCanvas) + LayoutConstants.EVENTOUTPORTCANVASOFFSETY + LayoutConstants.EVENTPORTHEIGHT + 3; eCL.Line.Y1 = Canvas.GetTop(((componentType)deploymentComponentList[evChannel.sources.source.component.id]).ComponentCanvas) + ((componentType)deploymentComponentList[evChannel.sources.source.component.id]).MainRectangle.Height + LayoutConstants.EVENTPORTHEIGHT + LayoutConstants.MAINRECTANGLEOFFSETY - 7; eCL.Line.X2 = Canvas.GetLeft(((componentType)deploymentComponentList[evChannel.targets.target.component.id]).ComponentCanvas) + LayoutConstants.EVENTINPORTCANVASOFFSETX + LayoutConstants.EVENTPORTWIDTH / 2 + 5; //eCL.Line.Y2 = Canvas.GetTop(((modelComponent)deploymentComponentList[evChannel.targets.target.component.id]).ComponentCanvas) + LayoutConstants.EVENTINPORTCANVASOFFSETY + LayoutConstants.EVENTPORTHEIGHT + 3; eCL.Line.Y2 = Canvas.GetTop(((componentType)deploymentComponentList[evChannel.targets.target.component.id]).ComponentCanvas) + ((componentType)deploymentComponentList[evChannel.targets.target.component.id]).MainRectangle.Height + LayoutConstants.EVENTPORTHEIGHT + LayoutConstants.MAINRECTANGLEOFFSETY - 7; eCL.Line.Focusable = true; eCL.ListenerComponentId = evChannel.targets.target.component.id; eCL.TriggerComponentId = evChannel.sources.source.component.id; eCL.Line.GotKeyboardFocus += EventChannel_GotKeyboardFocus; eCL.Line.LostKeyboardFocus += EventChannel_LostKeyboardFocus; eCL.Line.KeyDown += EventChannel_KeyDown; eCL.Line.ContextMenu = eventChannelContextMenu; eventChannelLinesList.Add(eCL); canvas.Children.Add(eCL.Line); KeyboardNavigation.SetTabIndex(eCL.Line, canvas.Children.Count + 1); Canvas.SetZIndex(eCL.Line, Canvas.GetZIndex(eCL.Line) + 2000); } eventChannelList.Add(o); foundLine = false; } else { // if no event listener Port can be found, the component has a version conflict MessageBox.Show(Properties.Resources.CopyEventsErrorTextFormat(evChannel.targets.target.component.id), Properties.Resources.CopyEventsErrorHeader, MessageBoxButton.OK, MessageBoxImage.Error); ((componentType)deploymentComponentList[evChannel.targets.target.component.id]).ComponentCanvas.Background = new SolidColorBrush(Colors.Orange); ((componentType)deploymentComponentList[evChannel.targets.target.component.id]).HasVersionConflict = true; } } else { // if no event trigger Port can be found, the component has a version conflict MessageBox.Show(Properties.Resources.CopyEventsErrorTextFormat(evChannel.sources.source.component.id), Properties.Resources.CopyEventsErrorHeader, MessageBoxButton.OK, MessageBoxImage.Error); ((componentType)deploymentComponentList[evChannel.sources.source.component.id]).ComponentCanvas.Background = new SolidColorBrush(Colors.Orange); ((componentType)deploymentComponentList[evChannel.sources.source.component.id]).HasVersionConflict = true; } } catch (Exception) { MessageBox.Show(Properties.Resources.CopyEventsExceptionTextFormat(evChannel.sources.source.component.id, evChannel.sources.source.eventPort.id, evChannel.targets.target.component.id, evChannel.targets.target.component.id), Properties.Resources.CopyEventsErrorHeader, MessageBoxButton.OK, MessageBoxImage.Error); } } deploymentModel.eventChannels = (eventChannel[])eventChannelList.ToArray(typeof(eventChannel)); } // focus the first element if (canvas.Children.Count > 0) { Keyboard.Focus(canvas.Children[0]); } else { Keyboard.Focus(canvas); } copyOffsetMulti++; ClearSelectedChannelList(); if (modelToPaste.channels != null) { foreach (channel c in modelToPaste.channels) { selectedChannelList.AddLast(c); co.InvolvedObjects.Add(c); } } UpdateSelectedChannels(); ClearSelectedEventChannelList(); LinkedList<eventChannelLine> selEventChannels = new LinkedList<eventChannelLine>(); foreach (eventChannelLine ecl in eventChannelLinesList) { if (modelToPaste.eventChannels != null) { foreach (eventChannel ech in modelToPaste.eventChannels) { if (ecl.ListenerComponentId == ech.targets.target.component.id || ecl.TriggerComponentId == ech.sources.source.component.id) { selEventChannels.AddLast(ecl); break; } } } } foreach (eventChannelLine ecl in selEventChannels) { selectedEventChannelList.AddLast(ecl); co.InvolvedObjects.Add(ecl); } UpdateSelectedEventChannels(); // select all inserted components ClearSelectedComponentList(); foreach (componentType mc in modelToPaste.components) { selectedComponentList.AddLast(mc); co.InvolvedObjects.Add(mc); } UpdateSelectedComponents(); if (addToUndoStack) { undoStack.Push(co); redoStack.Clear(); } SetKeyboardFocus(); int groupIndex = 0; AddDummyToModel(copyDummyName); foreach (ArrayList group in groupComps) { ClearSelectedChannelList(); ClearSelectedComponentList(); ClearSelectedEventChannelList(); foreach (componentType ct in group) { AddSelectedComponent(ct); } componentType groupComponent = (componentType) groups[groupIndex]; // add dummy channels to retain all ports of the copied group element foreach (object o in groupComponent.ports) { if (o is inputPortType) { inputPortType inPort = (inputPortType) o; string targetComponent = inPort.refs.componentID; componentType newTarget = null; foreach (componentType ct in group) { if (ct.id.StartsWith(targetComponent)) { if (newTarget == null) newTarget = ct; else { if (newTarget.id.Length < ct.id.Length) newTarget = ct; } } } if (newTarget == null) continue; // check if an channel already exists for this inputporttype bool duplicate = false; foreach (channel c in deploymentChannelList.Values) { if (c.target.component.id.Equals(newTarget.id) && c.target.port.id.Equals(inPort.portTypeID.Substring(targetComponent.Length + 1))) { duplicate = true; } } if (duplicate) continue; // add dummy channel channel groupChannel = new channel(); groupChannel.id = NewIdForChannel(); groupChannel.target.component.id = newTarget.id; groupChannel.target.port.id = inPort.refs.portID; groupChannel.source.component.id = copyDummyName; groupChannel.source.port.id = "out"; if (!ChannelExists(groupChannel)) AddChannel(groupChannel); } else if (o is outputPortType) { outputPortType outPort = (outputPortType) o; string sourceComponent = outPort.refs.componentID; componentType newSource = null; foreach (componentType ct in group) { if (ct.id.StartsWith(sourceComponent)) { if (newSource == null) newSource = ct; else { if (newSource.id.Length < ct.id.Length) newSource = ct; } } } if (newSource == null) continue; // add dummy channel channel groupChannel = new channel(); groupChannel.id = NewIdForChannel(); groupChannel.source.component.id = newSource.id; groupChannel.source.port.id = outPort.refs.portID; groupChannel.target.component.id = copyDummyName; groupChannel.target.port.id = "in"; if (!ChannelExists(groupChannel)) AddChannel(groupChannel); } } // add dummy eventchannels to retain all eventchannel ports of the copied group foreach (ArrayList echList in copyGroupEventChannels) { foreach (eventChannel ech in echList) { componentType source = null; componentType target = null; foreach (componentType ct in group) { if (ct.id.StartsWith(ech.sources.source.component.id)) { if (source == null) source = ct; else if (ct.id.Length > source.id.Length) source = ct; } if (ct.id.StartsWith(ech.targets.target.component.id)) { if (target == null) target = ct; else if (ct.id.Length > target.id.Length) target = ct; } } if (source != null) ech.sources.source.component.id = source.id; if (target != null) { ech.targets.target.component.id = target.id; ech.id = target.id + "_" + ech.sources.source.eventPort.id + "_" + ech.targets.target.eventPort.id; } if (source != null || target != null) eventChannelList.Add(ech); } } LinkedList<portAlias> newPortAlias = new LinkedList<portAlias>(); group originalGroup = null; foreach (object o in groups) { // groups.Add(ct); groupComponent gc = groupsList[((componentType)o).id]; // adapting the alias to the new group port names foreach (group gr in deploymentModel.groups) { if (gr.id == ((componentType)o).id) { originalGroup = gr; break; } } if (originalGroup != null && originalGroup.portAlias != null) { foreach (portAlias alias in originalGroup.portAlias) { foreach (string oldCompName in changedComponents.Keys) { if (alias.portId.Contains(oldCompName)) { portAlias pAlias = new portAlias(); pAlias.portId = alias.portId.Replace(oldCompName, changedComponents[oldCompName]); pAlias.portAlias1 = alias.portAlias1; newPortAlias.AddLast(pAlias); break; } } } } } DoGrouping((string) groupNames[groupIndex], false, true); group groupToUpdate = null; foreach (group gr in deploymentModel.groups) { if (gr.id == (string)groupNames[groupIndex]) { gr.portAlias = newPortAlias.ToArray(); groupToUpdate = gr; break; } } if (groupToUpdate.portAlias != null) { foreach (portAlias alias in groupToUpdate.portAlias) { componentType groupComponentToUpdate = deploymentComponentList[groupToUpdate.id]; groupComponentToUpdate.description = originalGroup.description; foreach (object port in groupComponentToUpdate.ports) { if ((port is inputPortType) && (((inputPortType)port).portTypeID == alias.portId)) { ((inputPortType)port).PortAliasForGroups = alias.portAlias1; ((inputPortType)port).PortLabel.Text = alias.portAlias1; break; } else if ((port is outputPortType) && (((outputPortType)port).portTypeID == alias.portId)) { ((outputPortType)port).PortAliasForGroups = alias.portAlias1; ((outputPortType)port).PortLabel.Text = alias.portAlias1; break; } } } } groupToUpdate.description = originalGroup.description; groupIndex++; } RemoveDummyFromModel(copyDummyName); DeleteDanglingChannels(); DeleteDanglingEventChannels(); // select the copied elements after paste selectedComponentList.Clear(); foreach (componentType mc in modelToPaste.components) { selectedComponentList.AddLast(mc); } UpdateSelectedComponents(); }
/// <summary> /// Add a new channel to the canvas and the data model /// </summary> /// <param name="newChannel"></param> private void AddChannel(channel newChannel) { if (deploymentChannelList.ContainsKey(newChannel.id)) return; deploymentChannelList.Add(newChannel.id, newChannel); if (!canvas.Children.Contains(newChannel.Line)) { canvas.Children.Add(newChannel.Line); newChannel.Line.StrokeDashArray = null; KeyboardNavigation.SetTabIndex(newChannel.Line, canvas.Children.Count + 1); } componentType tempComponent = deploymentComponentList[newChannel.source.component.id]; ((outputPortType)tempComponent.PortsList[newChannel.source.port.id]).ChannelIds.Add(newChannel.id); tempComponent = deploymentComponentList[newChannel.target.component.id]; // check, if there is already a channel connected to the port. If so, it must be a channel of a group, being connected to the input port object o = tempComponent.PortsList[newChannel.target.port.id]; if (o != null) { if (((inputPortType)o).ChannelId == "") { ((inputPortType)tempComponent.PortsList[newChannel.target.port.id]).ChannelId = newChannel.id; } else { ((inputPortType)tempComponent.PortsList[newChannel.target.port.id]).GroupChannelId = newChannel.id; } } // Set GroupOriginal Source string sourceCompId = newChannel.source.component.id; if (deploymentComponentList.ContainsKey(sourceCompId)) { if (groupsList.ContainsKey(deploymentComponentList[sourceCompId].id)) { int maxLength = 0; componentType tmpct = null; foreach (componentType ct in deploymentComponentList.Values) { if (newChannel.source.port.id.StartsWith(ct.id)) { if (ct.id.Length > maxLength) { tmpct = ct; maxLength = ct.id.Length; } } } if (tmpct != null) { bindingEdge be = new bindingEdge(); be.component = new bindingEdgeComponentType(); be.component.id = tmpct.id; be.port = new bindingEdgePortType(); be.port.id = newChannel.source.port.id.Substring(tmpct.id.Length + 1); newChannel.GroupOriginalSource = be; } } } // Set GroupOriginal Target string targetCompId = newChannel.target.component.id; if (deploymentComponentList.ContainsKey(targetCompId)) { if (groupsList.ContainsKey(deploymentComponentList[targetCompId].id)) { int maxLength = 0; componentType tmpct = null; foreach (componentType ct in deploymentComponentList.Values) { if (newChannel.target.port.id.StartsWith(ct.id)) { if (ct.id.Length > maxLength) { tmpct = ct; maxLength = ct.id.Length; } } } if (tmpct != null) { bindingEdge be = new bindingEdge(); be.component = new bindingEdgeComponentType(); be.component.id = tmpct.id; be.port = new bindingEdgePortType(); be.port.id = newChannel.target.port.id.Substring(tmpct.id.Length + 1); newChannel.GroupOriginalTarget = be; } } } // new channel has a group source and a component target if (newChannel.GroupOriginalSource != null) { // add channel also to the both original componenttypes channel groupChannel = new channel(); groupChannel.id = NewIdForGroupChannel(); groupChannel.source.component.id = newChannel.GroupOriginalSource.component.id; groupChannel.source.port.id = newChannel.GroupOriginalSource.port.id; groupChannel.target.component.id = newChannel.target.component.id; groupChannel.target.port.id = newChannel.target.port.id; if (!ChannelExists(groupChannel)) AddChannel(groupChannel); groupChannel.Line.Y1 = Canvas.GetTop(((outputPortType)(deploymentComponentList[groupChannel.source.component.id]).PortsList[groupChannel.source.port.id]).PortRectangle) + Canvas.GetTop((deploymentComponentList[groupChannel.source.component.id]).ComponentCanvas) + 5; groupChannel.Line.X1 = Canvas.GetLeft(((outputPortType)(deploymentComponentList[groupChannel.source.component.id]).PortsList[groupChannel.source.port.id]).PortRectangle) + Canvas.GetLeft((deploymentComponentList[groupChannel.source.component.id]).ComponentCanvas) + 20; groupChannel.Line.Y2 = Canvas.GetTop(((inputPortType)(deploymentComponentList[groupChannel.target.component.id]).PortsList[groupChannel.target.port.id]).PortRectangle) + Canvas.GetTop((deploymentComponentList[groupChannel.target.component.id]).ComponentCanvas) + 5; groupChannel.Line.X2 = Canvas.GetLeft(((inputPortType)(deploymentComponentList[groupChannel.target.component.id]).PortsList[groupChannel.target.port.id]).PortRectangle) + Canvas.GetLeft((deploymentComponentList[groupChannel.target.component.id]).ComponentCanvas); groupChannel.Line.Visibility = System.Windows.Visibility.Hidden; Canvas.SetZIndex(groupChannel.Line, Canvas.GetZIndex(groupChannel.Line) + 1000); } if (newChannel.GroupOriginalTarget != null) { // add channel also to the both original componenttypes channel groupChannel = new channel(); groupChannel.id = NewIdForGroupChannel(); groupChannel.source.component.id = newChannel.source.component.id; groupChannel.source.port.id = newChannel.source.port.id; groupChannel.target.component.id = newChannel.GroupOriginalTarget.component.id; groupChannel.target.port.id = newChannel.GroupOriginalTarget.port.id; if (!ChannelExists(groupChannel)) AddChannel(groupChannel); groupChannel.Line.Y1 = Canvas.GetTop(((outputPortType)(deploymentComponentList[groupChannel.source.component.id]).PortsList[groupChannel.source.port.id]).PortRectangle) + Canvas.GetTop((deploymentComponentList[groupChannel.source.component.id]).ComponentCanvas) + 5; groupChannel.Line.X1 = Canvas.GetLeft(((outputPortType)(deploymentComponentList[groupChannel.source.component.id]).PortsList[groupChannel.source.port.id]).PortRectangle) + Canvas.GetLeft((deploymentComponentList[groupChannel.source.component.id]).ComponentCanvas) + 20; groupChannel.Line.Y2 = Canvas.GetTop(((inputPortType)(deploymentComponentList[groupChannel.target.component.id]).PortsList[groupChannel.target.port.id]).PortRectangle) + Canvas.GetTop((deploymentComponentList[groupChannel.target.component.id]).ComponentCanvas) + 5; groupChannel.Line.X2 = Canvas.GetLeft(((inputPortType)(deploymentComponentList[groupChannel.target.component.id]).PortsList[groupChannel.target.port.id]).PortRectangle) + Canvas.GetLeft((deploymentComponentList[groupChannel.target.component.id]).ComponentCanvas); groupChannel.Line.Visibility = System.Windows.Visibility.Hidden; Canvas.SetZIndex(groupChannel.Line, Canvas.GetZIndex(groupChannel.Line) + 1000); } if (newChannel.GroupOriginalSource != null && newChannel.GroupOriginalTarget != null) { channel groupChannel = new channel(); groupChannel.id = NewIdForGroupChannel(); groupChannel.source.component.id = newChannel.GroupOriginalSource.component.id; groupChannel.source.port.id = newChannel.GroupOriginalSource.port.id; groupChannel.target.component.id = newChannel.GroupOriginalTarget.component.id; groupChannel.target.port.id = newChannel.GroupOriginalTarget.port.id; if (!ChannelExists(groupChannel)) AddChannel(groupChannel); groupChannel.Line.Y1 = Canvas.GetTop(((outputPortType)(deploymentComponentList[groupChannel.source.component.id]).PortsList[groupChannel.source.port.id]).PortRectangle) + Canvas.GetTop((deploymentComponentList[groupChannel.source.component.id]).ComponentCanvas) + 5; groupChannel.Line.X1 = Canvas.GetLeft(((outputPortType)(deploymentComponentList[groupChannel.source.component.id]).PortsList[groupChannel.source.port.id]).PortRectangle) + Canvas.GetLeft((deploymentComponentList[groupChannel.source.component.id]).ComponentCanvas) + 20; groupChannel.Line.Y2 = Canvas.GetTop(((inputPortType)(deploymentComponentList[groupChannel.target.component.id]).PortsList[groupChannel.target.port.id]).PortRectangle) + Canvas.GetTop((deploymentComponentList[groupChannel.target.component.id]).ComponentCanvas) + 5; groupChannel.Line.X2 = Canvas.GetLeft(((inputPortType)(deploymentComponentList[groupChannel.target.component.id]).PortsList[groupChannel.target.port.id]).PortRectangle) + Canvas.GetLeft((deploymentComponentList[groupChannel.target.component.id]).ComponentCanvas); groupChannel.Line.Visibility = System.Windows.Visibility.Hidden; Canvas.SetZIndex(groupChannel.Line, Canvas.GetZIndex(groupChannel.Line) + 1000); } newChannel.Line.ContextMenu = channelContextMenu; newChannel.Line.Focusable = true; newChannel.Line.GotKeyboardFocus += Channel_GotKeyboardFocus; newChannel.Line.LostKeyboardFocus += Channel_LostKeyboardFocus; newChannel.Line.KeyDown += Channel_KeyDown; // adding the new channel to the channel-array (required for the schema consistency) deploymentModel.channels = deploymentChannelList.Values.ToArray(); modelHasBeenEdited = true; }
/// <summary> /// Function called, if the left mouse button is pressed down on the canvas. This can cause several actions: move the component, draw a channel between ports or /// draw an event channel between two event ports /// </summary> /// <param name="sender"></param> /// <param name="args"></param> private void OnLeftDown(object sender, MouseEventArgs args) { if (hiddenChannels) { SetAllChannelsVisible(); hiddenChannels = false; } // four possibe actions: // select a component to move // connect the start point of a channel to an out-port // connect the end point of a channel to an in-port // fix a component after movement Point clickPoint = args.GetPosition(canvas); mouseMoveComponentX = (int)clickPoint.X; mouseMoveComponentY = (int)clickPoint.Y; connectedChannelLastClick = false; // sets a component to a new position // Line uncomment, to allow the drawing of channels just by clicking on the output port or the event trigger port //if ((newChannelRibbonButton.IsChecked == false) && (newEventChannelRibbonButton.IsChecked == false)) { if (args.Source is Canvas && ((Canvas)args.Source) == canvas && ModifierKeys.Control != Keyboard.Modifiers) { // whenever the user leaves the canvas with the mouse pointer, and stops holding the mousebutton, the mouseup // event will not get fired in this class. In this case the rectangle should not get modified // and work as before the user moved the mouse cursor outside the canvas. if (selectionRectangle == null) { ClearSelectedComponentList(); ClearSelectedChannelList(); ClearSelectedEventChannelList(); ResetPropertyDock(); selectionRectangle = new Rectangle(); Canvas.SetZIndex(selectionRectangle, selRectZIndex); selectionRectangle.Fill = new SolidColorBrush(Color.FromArgb(15, 0, 0, 255)); DoubleCollection dashes = new DoubleCollection(); dashes.Add(1.0000001); dashes.Add(2.0000001); selectionRectangle.StrokeDashArray = dashes; selectionRectangle.Stroke = new SolidColorBrush(Colors.Black); selectionRectangle.Width = 1; selectionRectangle.Height = 1; selRectStartPoint = args.GetPosition(canvas); Canvas.SetLeft(selectionRectangle, selRectStartPoint.X); Canvas.SetTop(selectionRectangle, selRectStartPoint.Y); canvas.Children.Add(selectionRectangle); } } else if (args.Source is Rectangle) { //modelComponent tempComponent = null; if ((Keyboard.Modifiers & ModifierKeys.Control) == 0) { foreach (componentType tempComponent in deploymentComponentList.Values) { if ((tempComponent.MainRectangle == (Rectangle)args.Source) || (tempComponent.TopRectangle == (Rectangle)args.Source)) { focusedComponent = tempComponent; Keyboard.Focus(focusedComponent.ComponentCanvas); if (!selectedComponentList.Contains(tempComponent)) { ClearSelectedComponentList(); ClearSelectedChannelList(); ClearSelectedEventChannelList(); this.AddSelectedComponent(tempComponent); moveComponentRibbonButton.IsChecked = true; moveTracking = false; } break; } else { if (newChannelRibbonButton.IsEnabled) // was editchannelribbongroup { foreach (object o in tempComponent.PortsList.Values) { if (o is outputPortType) { if (((outputPortType)o).PortRectangle == (Rectangle)args.Source) { //focusedComponent = tempComponent; //Keyboard.Focus(focusedComponent.ComponentCanvas); newChannelRibbonButton.IsChecked = true; //disable mouse move mouseMoveComponentX = -1; mouseMoveComponentY = -1; ClearSelectedChannelList(); ClearSelectedComponentList(); ClearSelectedEventChannelList(); break; } } else if (o is inputPortType) { if (((inputPortType)o).PortRectangle == (Rectangle)args.Source) { //disable mouse move if (!selectedComponentList.Contains(tempComponent) && channelToConnect == null) { ClearSelectedComponentList(); ClearSelectedChannelList(); ClearSelectedEventChannelList(); this.AddSelectedComponent(tempComponent); moveComponentRibbonButton.IsChecked = true; } } } } } } } } } else if (args.Source is TextBlock) { if ((Keyboard.Modifiers & ModifierKeys.Control) == 0) { foreach (componentType tempComponent in deploymentComponentList.Values) { if (tempComponent.Label == (TextBlock)args.Source) { focusedComponent = tempComponent; Keyboard.Focus(focusedComponent.ComponentCanvas); if (!selectedComponentList.Contains(tempComponent)) { ClearSelectedComponentList(); ClearSelectedChannelList(); ClearSelectedEventChannelList(); this.AddSelectedComponent(tempComponent); moveComponentRibbonButton.IsChecked = true; } break; } else { foreach (object o in tempComponent.PortsList.Values) { if (o is inputPortType) { if (((inputPortType)o).PortLabel == (TextBlock)args.Source) { focusedComponent = tempComponent; Keyboard.Focus(focusedComponent.ComponentCanvas); if (!selectedComponentList.Contains(tempComponent)) { ClearSelectedComponentList(); ClearSelectedChannelList(); ClearSelectedEventChannelList(); this.AddSelectedComponent(tempComponent); moveComponentRibbonButton.IsChecked = true; } break; } } else if (o is outputPortType) { if (((outputPortType)o).PortLabel == (TextBlock)args.Source) { focusedComponent = tempComponent; Keyboard.Focus(focusedComponent.ComponentCanvas); if (!selectedComponentList.Contains(tempComponent)) { ClearSelectedComponentList(); ClearSelectedChannelList(); ClearSelectedEventChannelList(); this.AddSelectedComponent(tempComponent); moveComponentRibbonButton.IsChecked = true; } break; } } } } } } } else if (args.Source is Polygon) { if (newEventChannelRibbonButton.IsEnabled) // was editeventribbongroup { if (((Polygon)args.Source).Name == "EventTriggerPortPolygon") { newEventChannelRibbonButton.IsChecked = true; ClearSelectedEventChannelList(); ClearSelectedComponentList(); ClearSelectedChannelList(); } else { if (newEventChannelRibbonButton.IsChecked == false) { // mouse down on an event channel input, not in connect mode if ((Keyboard.Modifiers & ModifierKeys.Control) == 0) { foreach (componentType tempComponent in deploymentComponentList.Values) { Canvas tempCanvas = (Canvas)((Polygon)args.Source).Parent; if (tempComponent.ComponentCanvas == tempCanvas.Parent) { focusedComponent = tempComponent; Keyboard.Focus(focusedComponent.ComponentCanvas); if (!selectedComponentList.Contains(tempComponent)) { ClearSelectedComponentList(); ClearSelectedChannelList(); ClearSelectedEventChannelList(); this.AddSelectedComponent(tempComponent); moveComponentRibbonButton.IsChecked = true; } break; } } } } } } } if (focusedComponent != null) { Canvas.SetZIndex(focusedComponent.ComponentCanvas, Canvas.GetZIndex(focusedComponent.ComponentCanvas) + 3000); } if (componentToMove == null && focusedComponent != null) { if (args.Source is Rectangle) { if ((focusedComponent.MainRectangle == (Rectangle)args.Source) || (focusedComponent.TopRectangle == (Rectangle)args.Source)) { componentToMove = focusedComponent; offsetX = (int)args.GetPosition(canvas).X - (int)Canvas.GetLeft(focusedComponent.ComponentCanvas); offsetY = (int)args.GetPosition(canvas).Y - (int)Canvas.GetTop(focusedComponent.ComponentCanvas); } } else if (args.Source is TextBlock) { if ((focusedComponent.ComponentCanvas == ((TextBlock)args.Source).Parent) || (focusedComponent.Label) == (TextBlock)args.Source) { componentToMove = focusedComponent; offsetX = (int)args.GetPosition(canvas).X - (int)Canvas.GetLeft(focusedComponent.ComponentCanvas); offsetY = (int)args.GetPosition(canvas).Y - (int)Canvas.GetTop(focusedComponent.ComponentCanvas); } } //MoveComponent(componentToMove, (int)args.GetPosition(canvas).X, (int)args.GetPosition(canvas).Y); //componentToMove = null; } //} if ((newChannelRibbonButton.IsChecked == true) && (newChannelRibbonButton.IsEnabled)) // was editchannelribbongroup { // outport has been found, component channel has been created, now searching for inport and make all connections/settings if (channelToConnect != null) { if (args.Source is Rectangle) { Rectangle r = (Rectangle)args.Source; Canvas tempCanvas = (Canvas)r.Parent; foreach (componentType tempComponent in deploymentComponentList.Values) { if (tempComponent.ComponentCanvas == tempCanvas) { bool portfound = false; if (tempComponent.ports != null) { foreach (object o in tempComponent.ports) { if (o is inputPortType) { inputPortType inPort = (inputPortType)o; if ((inPort.PortRectangle == r) && (inPort.ChannelId == "")) { outputPortType outPort = (outputPortType)((componentType)deploymentComponentList[channelToConnect.source.component.id]).PortsList[channelToConnect.source.port.id]; //outputPortType outPort = (outputPortType)((modelComponent)deploymentComponentList[channelToConnect.source.component.id]).ports.PortsList[] if (CheckInteroperabilityOfPorts(outPort.PortDataType, inPort.PortDataType)) { channelToConnect.target.component.id = tempComponent.id; channelToConnect.target.port.id = inPort.portTypeID; channelToConnect.Line.X2 = Canvas.GetLeft(r) + Canvas.GetLeft(tempCanvas); channelToConnect.Line.Y2 = Canvas.GetTop(r) + r.ActualHeight - r.ActualHeight / 2 + Canvas.GetTop(tempCanvas); inPort.ChannelId = channelToConnect.id; AddChannel(channelToConnect); portfound = true; Canvas.SetZIndex(channelToConnect.Line, Canvas.GetZIndex(channelToConnect.Line) + 1000); CommandObject co = new CommandObject("Delete", channelToConnect); undoStack.Push(co); redoStack.Clear(); channelToConnect = null; newChannelRibbonButton.IsChecked = false; connectedChannelLastClick = true; ChangeChannelVisibility(outPort.PortDataType, false, true, false); break; } else { MessageBox.Show(Properties.Resources.PortConnectingDatyTypeErrorFormat(outPort.PortDataType, inPort.PortDataType), Properties.Resources.PortConnectingDatyTypeErrorHeader, MessageBoxButton.OK, MessageBoxImage.Error); } } } } } if (portfound == false) { // click on a component while trying to connect a channel ClearSelectedChannelList(); ClearSelectedComponentList(); ClearSelectedEventChannelList(); AddSelectedComponent(tempComponent); canvas.Children.Remove(channelToConnect.Line); channelToConnect = null; newChannelRibbonButton.IsChecked = false; //TODO: restore visibility of ports } break; } } // click on the empty canvas, componentChannel will be deleted instead of connected } else { canvas.Children.Remove(channelToConnect.Line); channelToConnect = null; newChannelRibbonButton.IsChecked = false; } } // searching an out-port for a new channel else if (args.Source is Rectangle) { Rectangle r = (Rectangle)args.Source; Canvas tempCanvas = (Canvas)r.Parent; foreach (componentType tempComponent in deploymentComponentList.Values) { if (tempComponent.ComponentCanvas == tempCanvas) { foreach (object o in tempComponent.ports) { if (o is outputPortType) { outputPortType outPort = (outputPortType)o; if (outPort.PortRectangle == r) { channelToConnect = new channel(); channelToConnect.id = NewIdForChannel(); channelToConnect.source.component.id = tempComponent.id; channelToConnect.source.port.id = outPort.portTypeID; //outPort.ChannelId = channelToConnect.id; channelToConnect.Line.X1 = Canvas.GetLeft(r) + r.ActualWidth + Canvas.GetLeft(tempCanvas); channelToConnect.Line.Y1 = Canvas.GetTop(r) + r.ActualHeight - r.ActualHeight / 2 + Canvas.GetTop(tempCanvas); // -5 channelToConnect.Line.X2 = args.GetPosition(canvas).X; channelToConnect.Line.Y2 = args.GetPosition(canvas).Y; canvas.Children.Add(channelToConnect.Line); ChangeChannelVisibility(outPort.PortDataType, true, false, true); break; } } } break; } } } } else if ((newChannelRibbonButton.IsChecked == false) && (channelToConnect != null)) { // click on the empty canvas, componentChannel will be deleted instead of connected canvas.Children.Remove(channelToConnect.Line); channelToConnect = null; newChannelRibbonButton.IsChecked = false; } if ((newEventChannelRibbonButton.IsChecked == true) && (newEventChannelRibbonButton.IsEnabled)) // was editeventribbongroup { if (args.Source is Polygon) { if (eventChannelToConnect == null) { Polygon p = (Polygon)args.Source; Canvas tempCanvas = (Canvas)p.Parent; if (tempCanvas.Name == "EventTriggerPort") { eventChannelToConnect = new eventChannelLine(); foreach (componentType tempComponent in deploymentComponentList.Values) { if (tempComponent.ComponentCanvas == (Canvas)tempCanvas.Parent) { eventChannelToConnect.TriggerComponentId = tempComponent.id; break; } } eventChannelToConnect.Line.X1 = Canvas.GetLeft((Canvas)tempCanvas.Parent) + Canvas.GetLeft(tempCanvas) + tempCanvas.Width / 2 + 2; eventChannelToConnect.Line.Y1 = Canvas.GetTop((Canvas)tempCanvas.Parent) + Canvas.GetTop(tempCanvas) + tempCanvas.Height; eventChannelToConnect.Line.X2 = args.GetPosition(canvas).X; eventChannelToConnect.Line.Y2 = args.GetPosition(canvas).Y; canvas.Children.Add(eventChannelToConnect.Line); } } else { // connect Polygon p = (Polygon)args.Source; Canvas tempCanvas = (Canvas)p.Parent; if (tempCanvas.Name == "EventListenerPort") { foreach (componentType tempComponent in deploymentComponentList.Values) { if (tempComponent.ComponentCanvas == (Canvas)tempCanvas.Parent) { eventChannelToConnect.ListenerComponentId = tempComponent.id; break; } } eventChannelToConnect.Line.X2 = Canvas.GetLeft((Canvas)tempCanvas.Parent) + Canvas.GetLeft(tempCanvas) + tempCanvas.ActualWidth / 2 + 2; eventChannelToConnect.Line.Y2 = Canvas.GetTop((Canvas)tempCanvas.Parent) + Canvas.GetTop(tempCanvas) + tempCanvas.Height; connectedChannelLastClick = true; CommandObject co = new CommandObject("Delete", eventChannelToConnect); undoStack.Push(co); redoStack.Clear(); AddEventChannelCommand(eventChannelToConnect, true); eventChannelToConnect = null; newEventChannelRibbonButton.IsChecked = false; ////dockManager.ActiveContent = dockableEventsTab; } } } else { // drop the eventChannelLine if (eventChannelToConnect != null) { canvas.Children.Remove(eventChannelToConnect.Line); eventChannelToConnect = null; newEventChannelRibbonButton.IsChecked = false; } } } else if ((newEventChannelRibbonButton.IsChecked == false) && (eventChannelToConnect != null)) { // click on the empty canvas, eventChannel will be deleted instead of connected canvas.Children.Remove(eventChannelToConnect.Line); eventChannelToConnect = null; newEventChannelRibbonButton.IsChecked = false; } }
/// <summary> /// Function called, when the left mouse button will be released. If the release will be done over a channel or an event channel, the channel will get the focus /// </summary> /// <param name="sender"></param> /// <param name="args"></param> private void OnLeftUp(object sender, MouseEventArgs args) { // reset mouseMove Coordinates mouseMoveComponentX = -1; mouseMoveComponentY = -1; // when on the LeftDown Event a channel docked to a component all Selected Items should get deselected if (connectedChannelLastClick == true) { connectedChannelLastClick = false; ClearSelectedChannelList(); ClearSelectedComponentList(); ClearSelectedEventChannelList(); return; } // left up on an event channel. set event channel as focused event channel if (args.Source is Line) { if (((Line)args.Source).Name == "EventChannelLine") { foreach (eventChannelLine tempLine in eventChannelLinesList) { if (tempLine.Line == (Line)args.Source) { focusedEventChannel = tempLine; Keyboard.Focus(focusedEventChannel.Line); if (!selectedEventChannelList.Contains(tempLine)) { if ((Keyboard.Modifiers & ModifierKeys.Control) == 0) { ClearSelectedChannelList(); ClearSelectedComponentList(); ClearSelectedEventChannelList(); } AddSelectedEventChannel(tempLine); } else { if ((Keyboard.Modifiers & ModifierKeys.Control) > 0) { ClearColorOfSelectedEventChannels(); selectedEventChannelList.Remove(tempLine); UpdateSelectedEventChannels(); } } break; } } } else { // left up on a channel. set channel as focused channel foreach (channel tempChannel in deploymentChannelList.Values) { if (tempChannel.Line == (Line)args.Source) { focusedChannel = tempChannel; Keyboard.Focus(focusedChannel.Line); if (!selectedChannelList.Contains(tempChannel)) { if ((Keyboard.Modifiers & ModifierKeys.Control) == 0) { ClearSelectedChannelList(); ClearSelectedComponentList(); ClearSelectedEventChannelList(); } this.AddSelectedChannel(tempChannel); Console.WriteLine(tempChannel.id + ": " + tempChannel.source.component.id + " --> " + tempChannel.target.component.id); } else { if ((Keyboard.Modifiers & ModifierKeys.Control) > 0) { ClearColorOfSelectedChannels(); selectedChannelList.Remove(tempChannel); UpdateSelectedChannels(); } } break; } } } } else if (args.Source is Rectangle) { //modelComponent tempComponent = null; moveTracking = false; foreach (componentType tempComponent in deploymentComponentList.Values) { if ((tempComponent.MainRectangle == (Rectangle)args.Source) || (tempComponent.TopRectangle == (Rectangle)args.Source)) { focusedComponent = tempComponent; Keyboard.Focus(focusedComponent.ComponentCanvas); if (!selectedComponentList.Contains(tempComponent)) { if ((Keyboard.Modifiers & ModifierKeys.Control) == 0) { ClearSelectedComponentList(); ClearSelectedChannelList(); ClearSelectedEventChannelList(); } AddSelectedComponent(tempComponent); } else { if ((Keyboard.Modifiers & ModifierKeys.Control) > 0) { ClearBorderOfSelectedComponents(); selectedComponentList.Remove(tempComponent); UpdateSelectedComponents(); } } break; } else { if (newChannelRibbonButton.IsEnabled) // was editchannelribbongroup { foreach (object o in tempComponent.PortsList.Values) { if (o is outputPortType) { if (((outputPortType)o).PortRectangle == (Rectangle)args.Source) { //focusedComponent = tempComponent; //Keyboard.Focus(focusedComponent.ComponentCanvas); newChannelRibbonButton.IsChecked = true; break; } } else if (o is inputPortType) { if (((inputPortType)o).PortRectangle == (Rectangle)args.Source) { if (!selectedComponentList.Contains(tempComponent)) { if ((Keyboard.Modifiers & ModifierKeys.Control) == 0) { ClearSelectedComponentList(); ClearSelectedChannelList(); ClearSelectedEventChannelList(); } AddSelectedComponent(tempComponent); } else { if ((Keyboard.Modifiers & ModifierKeys.Control) > 0) { ClearBorderOfSelectedComponents(); selectedComponentList.Remove(tempComponent); UpdateSelectedComponents(); } } focusedComponent = tempComponent; Keyboard.Focus(tempComponent.ComponentCanvas); } } } } } } } else if (args.Source is TextBlock) { foreach (componentType tempComponent in deploymentComponentList.Values) { if (tempComponent.Label == (TextBlock)args.Source) { focusedComponent = tempComponent; Keyboard.Focus(focusedComponent.ComponentCanvas); if (!selectedComponentList.Contains(tempComponent)) { if ((Keyboard.Modifiers & ModifierKeys.Control) == 0) { ClearSelectedComponentList(); ClearSelectedChannelList(); ClearSelectedEventChannelList(); } AddSelectedComponent(tempComponent); } else { if ((Keyboard.Modifiers & ModifierKeys.Control) > 0) { ClearBorderOfSelectedComponents(); selectedComponentList.Remove(tempComponent); UpdateSelectedComponents(); } } break; } else { foreach (object o in tempComponent.PortsList.Values) { if (o is inputPortType) { if (((inputPortType)o).PortLabel == (TextBlock)args.Source) { focusedComponent = tempComponent; Keyboard.Focus(focusedComponent.ComponentCanvas); if (!selectedComponentList.Contains(tempComponent)) { if ((Keyboard.Modifiers & ModifierKeys.Control) == 0) { ClearSelectedComponentList(); ClearSelectedChannelList(); ClearSelectedEventChannelList(); } AddSelectedComponent(tempComponent); } else { if ((Keyboard.Modifiers & ModifierKeys.Control) > 0) { ClearBorderOfSelectedComponents(); selectedComponentList.Remove(tempComponent); UpdateSelectedComponents(); } } break; } } else if (o is outputPortType) { if (((outputPortType)o).PortLabel == (TextBlock)args.Source) { focusedComponent = tempComponent; Keyboard.Focus(focusedComponent.ComponentCanvas); if (!selectedComponentList.Contains(tempComponent)) { if ((Keyboard.Modifiers & ModifierKeys.Control) == 0) { ClearSelectedComponentList(); ClearSelectedChannelList(); ClearSelectedEventChannelList(); } AddSelectedComponent(tempComponent); } else { if ((Keyboard.Modifiers & ModifierKeys.Control) > 0) { ClearBorderOfSelectedComponents(); selectedComponentList.Remove(tempComponent); UpdateSelectedComponents(); } } break; } } } } } } else if (args.Source is Polygon) { if (newEventChannelRibbonButton.IsEnabled) // was editeventribbongroup { if (!((Polygon)args.Source).Name.Equals("EventTriggerPortPolygon")) { foreach (componentType tempComponent in deploymentComponentList.Values) { Canvas tempCanvas = (Canvas)((Polygon)args.Source).Parent; if (tempComponent.ComponentCanvas == tempCanvas.Parent) { if (!selectedComponentList.Contains(tempComponent)) { if ((Keyboard.Modifiers & ModifierKeys.Control) == 0) { ClearSelectedComponentList(); ClearSelectedChannelList(); ClearSelectedEventChannelList(); } AddSelectedComponent(tempComponent); focusedComponent = tempComponent; Keyboard.Focus(focusedComponent.ComponentCanvas); } else { if ((Keyboard.Modifiers & ModifierKeys.Control) > 0) { ClearBorderOfSelectedComponents(); selectedComponentList.Remove(tempComponent); UpdateSelectedComponents(); } else { focusedComponent = tempComponent; Keyboard.Focus(tempComponent.ComponentCanvas); } } break; } } } } } if (selectionRectangle != null) { //select all objects of the canvas which collide with this rectangle this.selectObjectsFromRectangle(selectionRectangle); canvas.Children.Remove(selectionRectangle); selectionRectangle = null; } if (componentToMove != null) { focusedComponent = componentToMove; Keyboard.Focus(focusedComponent.ComponentCanvas); Canvas.SetZIndex(focusedComponent.ComponentCanvas, Canvas.GetZIndex(focusedComponent.ComponentCanvas) - 3000); componentToMove = null; } offsetX = 0; offsetY = 0; }
/// <summary> /// Delete a channel from the canvas and the data model /// </summary> /// <param name="deleteChannel"></param> /*private void DeleteChannel(channel deleteChannel) { // delete the reference in the source and target components componentType tempComponent = deploymentComponentList[deleteChannel.source.component.id]; ((outputPortType)tempComponent.PortsList[deleteChannel.source.port.id]).ChannelIds.Remove(deleteChannel.id); tempComponent = deploymentComponentList[deleteChannel.target.component.id]; if (deleteChannel.id.StartsWith("group") && (((inputPortType)tempComponent.PortsList[deleteChannel.target.port.id]).GroupChannelId != "")) { // && !deleteChannel.target.component.id.StartsWith("group")) { ((inputPortType)tempComponent.PortsList[deleteChannel.target.port.id]).GroupChannelId = ""; } else { ((inputPortType)tempComponent.PortsList[deleteChannel.target.port.id]).ChannelId = ""; } if (deleteChannel.id.StartsWith("group") && deleteChannel.source.component.id.StartsWith("group") ) { componentType tempRefComponent = deploymentComponentList[((outputPortType)deploymentComponentList[deleteChannel.source.component.id].PortsList[deleteChannel.source.port.id]).refs.componentID]; outputPortType tempOutPort = (outputPortType)tempRefComponent.PortsList[((outputPortType)deploymentComponentList[deleteChannel.source.component.id].PortsList[deleteChannel.source.port.id]).refs.portID]; //outputPortType tempOutPort = (outputPortType)deploymentComponentList[((outputPortType)tempComponent.PortsList[deleteChannel.source.port.id]).refs.componentID].PortsList[((outputPortType)tempComponent.PortsList[deleteChannel.source.port.id]).refs.portID]; tempOutPort.ChannelIds.Remove(deleteChannel.id); } // delete the channel itself canvas.Children.Remove(deleteChannel.Line); deploymentChannelList.Remove(deleteChannel.id); // copy hashtable to array deploymentModel.channels = deploymentChannelList.Values.ToArray(); // remove listeners deleteChannel.Line.GotKeyboardFocus -= Channel_GotKeyboardFocus; deleteChannel.Line.LostKeyboardFocus -= Channel_LostKeyboardFocus; deleteChannel.Line.KeyDown -= Channel_KeyDown; modelHasBeenEdited = true; }*/ private void DeleteChannel(channel deleteChannel) { // delete the reference in the source and target components if (deploymentComponentList.ContainsKey(deleteChannel.source.component.id)) { componentType tempComponent = null; tempComponent = deploymentComponentList[deleteChannel.source.component.id]; ((outputPortType)tempComponent.PortsList[deleteChannel.source.port.id]).ChannelIds.Remove(deleteChannel.id); } if (deploymentComponentList.ContainsKey(deleteChannel.target.component.id)) { componentType tempComponent = null; tempComponent = deploymentComponentList[deleteChannel.target.component.id]; if (deleteChannel.id.StartsWith("group") && (((inputPortType)tempComponent.PortsList[deleteChannel.target.port.id]).GroupChannelId != "")) { // && !deleteChannel.target.component.id.StartsWith("group")) { ((inputPortType)tempComponent.PortsList[deleteChannel.target.port.id]).GroupChannelId = ""; } else { ((inputPortType)tempComponent.PortsList[deleteChannel.target.port.id]).ChannelId = ""; } } if (deleteChannel.id.StartsWith("group") && deleteChannel.source.component.id.StartsWith("group")) { if (deploymentComponentList.ContainsKey(deleteChannel.source.component.id)) { componentType tempRefComponent = deploymentComponentList[((outputPortType)deploymentComponentList[deleteChannel.source.component.id].PortsList[deleteChannel.source.port.id]).refs.componentID]; outputPortType tempOutPort = (outputPortType)tempRefComponent.PortsList[((outputPortType)deploymentComponentList[deleteChannel.source.component.id].PortsList[deleteChannel.source.port.id]).refs.portID]; tempOutPort.ChannelIds.Remove(deleteChannel.id); } //outputPortType tempOutPort = (outputPortType)deploymentComponentList[((outputPortType)tempComponent.PortsList[deleteChannel.source.port.id]).refs.componentID].PortsList[((outputPortType)tempComponent.PortsList[deleteChannel.source.port.id]).refs.portID]; } foreach (groupComponent gc in groupsList.Values) { gc.AddedChannelsList.Remove(deleteChannel); } // delete the channel itself canvas.Children.Remove(deleteChannel.Line); deploymentChannelList.Remove(deleteChannel.id); // copy hashtable to array deploymentModel.channels = deploymentChannelList.Values.ToArray(); // remove listeners deleteChannel.Line.GotKeyboardFocus -= Channel_GotKeyboardFocus; deleteChannel.Line.LostKeyboardFocus -= Channel_LostKeyboardFocus; deleteChannel.Line.KeyDown -= Channel_KeyDown; modelHasBeenEdited = true; }
/// <summary> /// Global keyboard listener within the application. Used to handle 'Esc'-key, F-keys, Zoom and Shortcuts for avalon-windows /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void Global_KeyDown(object sender, KeyEventArgs e) { if (e.Key == Key.Escape) { if (channelToConnect != null) { canvas.Children.Remove(channelToConnect.Line); channelToConnect = null; } if (eventChannelToConnect != null) { canvas.Children.Remove(eventChannelToConnect.Line); eventChannelToConnect = null; } } if ((Keyboard.Modifiers == ModifierKeys.Control) && (e.Key == Key.P)) { Keyboard.Focus(dockableComponentProperties); } else if ((Keyboard.Modifiers == ModifierKeys.Control) && (e.Key == Key.E)) { Keyboard.Focus(dockableEventsTab); } else if ((Keyboard.Modifiers == ModifierKeys.Control) && (e.Key == Key.D)) { Keyboard.Focus(scrollCanvars); // Timer is setting the focus to the first element. Otherwise, the system is still changing the tabs // and the focus will not be set, as the elements are not visible TimerCallback tcbFocus = this.DoFocusTimer; statusTimer = new Timer(tcbFocus, canvas, 300, Timeout.Infinite); } else if ((Keyboard.Modifiers == ModifierKeys.Control) && (e.Key == Key.G)) { Keyboard.Focus(GUIEditorCanvas); // Timer is setting the focus to the first element. Otherwise, the system is still changing the tabs // and the focus will not be set, as the elements are not visible TimerCallback tcbFocus = this.DoFocusTimer; statusTimer = new Timer(tcbFocus, guiCanvas, 300, Timeout.Infinite); } else if ((Keyboard.Modifiers == ModifierKeys.Control) && ((e.Key == Key.Add) || (e.Key == Key.OemPlus))) { if (zoomSlider.Value < zoomSlider.Maximum) { zoomSlider.Value += zoomSlider.SmallChange; } } else if ((Keyboard.Modifiers == ModifierKeys.Control) && ((e.Key == Key.Subtract) || (e.Key == Key.OemMinus))) { if (zoomSlider.Value > zoomSlider.Minimum) { zoomSlider.Value -= zoomSlider.SmallChange; } } else if (e.Key == Key.F1) { Help_Click(sender, null); } else if (e.Key == Key.F5) { if (runModelButton.IsEnabled) { StartModel_Click(null, null); } } else if (e.Key == Key.F6) { if (pauseModelButton.IsEnabled) { PauseModel_Click(null, null); } } else if (e.Key == Key.F7) { if (stopModelButton.IsEnabled) { StopModel_Click(null, null); } } else if (e.Key == Key.A && ModifierKeys.Control == e.KeyboardDevice.Modifiers) { SelectAll(); } else if (e.Key == Key.C && ModifierKeys.Control == e.KeyboardDevice.Modifiers) { if (!((areStatus.Status == AREStatus.ConnectionStatus.Running) || (areStatus.Status == AREStatus.ConnectionStatus.Pause))) { CopySelectedCommand(); e.Handled = true; pasteRibbonButton.IsEnabled = true; } } else if (e.Key == Key.V && ModifierKeys.Control == e.KeyboardDevice.Modifiers) { if (!((areStatus.Status == AREStatus.ConnectionStatus.Running) || (areStatus.Status == AREStatus.ConnectionStatus.Pause))) { model tmpModel = CopyModel(copyModel); PasteCopiedModel(copyModel, false,true); copyModel = tmpModel; } } else if (e.Key == Key.X && ModifierKeys.Control == e.KeyboardDevice.Modifiers) { if (!((areStatus.Status == AREStatus.ConnectionStatus.Running) || (areStatus.Status == AREStatus.ConnectionStatus.Pause))) { CopySelectedCommand(); DeleteSelectedComponents(); pasteRibbonButton.IsEnabled = true; } } else if (e.Key == Key.Delete) { if (!((areStatus.Status == AREStatus.ConnectionStatus.Running) || (areStatus.Status == AREStatus.ConnectionStatus.Pause))) { DeleteSelectedComponents(); } } else if (e.Key == Key.Z && ModifierKeys.Control == e.KeyboardDevice.Modifiers) { if (undoButton.IsEnabled) { Undo_Click(sender, e); } } else if (e.Key == Key.Y && ModifierKeys.Control == e.KeyboardDevice.Modifiers) { if (redoButton.IsEnabled) { Redo_Click(sender, e); } } else if (e.Key == Key.S && ModifierKeys.Control == e.KeyboardDevice.Modifiers) { // If a property has been edited and the focus has not been set to another element, the property will not be set. // Clicking ribbon elments did not remove focus from property editor, so the property will // not be set. Causes problems, saving, uplaoding, ... the model if (canvas.Children.Count > 0) { Keyboard.Focus(canvas.Children[0]); } else { Keyboard.Focus(canvas); } String mustBeConnectedError = MustBeConnectedChecker(); if (mustBeConnectedError != "") { MessageBox.Show(mustBeConnectedError, Properties.Resources.MustBeConnectedCheckerHeader, MessageBoxButton.OK, MessageBoxImage.Error); } else { // if no file for saving is defined yet, show the saveas-dialog if (saveFile != null) { SaveLocalCommand(false); } else { SaveLocalCommand(true); } } } }
/// <summary> /// Connect channel from the component context menu - needed to make the ACS fully keyboard accessible /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void ComponentContextMenuConnectChannel_Click(object sender, RoutedEventArgs e) { componentType componentWithFocus = null; // Check, if context menu was called from a rectangel if (((ContextMenu)((MenuItem)((MenuItem)e.Source).Parent).Parent).PlacementTarget is Rectangle) { Rectangle r = (Rectangle)((ContextMenu)((MenuItem)((MenuItem)e.Source).Parent).Parent).PlacementTarget; foreach (componentType tempComponent in deploymentComponentList.Values) { if ((tempComponent.MainRectangle == r) || (tempComponent.TopRectangle == r)) { componentWithFocus = tempComponent; break; } } // Check, if context menu was called from a grid (the name field at the top of a component) } else if (((ContextMenu)((MenuItem)((MenuItem)e.Source).Parent).Parent).PlacementTarget is Grid) { Grid g = (Grid)((ContextMenu)((MenuItem)((MenuItem)e.Source).Parent).Parent).PlacementTarget; foreach (componentType tempComponent in deploymentComponentList.Values) { if (tempComponent.TopGrid == g) { componentWithFocus = tempComponent; break; } } } // if no channel is prepared to be connected, a new channel will be prepared if (channelToConnect == null) { channelToConnect = new channel(); channelToConnect.id = NewIdForChannel(); channelToConnect.source.component.id = componentWithFocus.id; channelToConnect.source.port.id = ((MenuItem)e.Source).Header.ToString(); Rectangle portRectangle = ((outputPortType)componentWithFocus.PortsList[channelToConnect.source.port.id]).PortRectangle; channelToConnect.Line.X1 = Canvas.GetLeft(portRectangle) + portRectangle.ActualWidth + Canvas.GetLeft(componentWithFocus.ComponentCanvas); channelToConnect.Line.Y1 = Canvas.GetTop(portRectangle) + portRectangle.ActualHeight - 5 + Canvas.GetTop(componentWithFocus.ComponentCanvas); newChannelRibbonButton.IsChecked = true; componentContextMenuItemAddChannel.IsEnabled = false; componentContextMenuItemConnectChannel.IsEnabled = true; componentContextMenuItemDropChannel.IsEnabled = true; // if a channel is prepared, it will tried to connect it } else { outputPortType outPort = (outputPortType)((componentType)deploymentComponentList[channelToConnect.source.component.id]).PortsList[channelToConnect.source.port.id]; channelToConnect.target.component.id = componentWithFocus.id; channelToConnect.target.port.id = ((MenuItem)e.Source).Header.ToString(); // check, if the datatypes of the port fits to each other if (CheckInteroperabilityOfPorts(outPort.PortDataType, ((inputPortType)componentWithFocus.PortsList[channelToConnect.target.port.id]).PortDataType)) { Rectangle portRectangle = ((inputPortType)componentWithFocus.PortsList[channelToConnect.target.port.id]).PortRectangle; channelToConnect.Line.X2 = Canvas.GetLeft(portRectangle) + Canvas.GetLeft(componentWithFocus.ComponentCanvas); channelToConnect.Line.Y2 = Canvas.GetTop(portRectangle) + portRectangle.ActualHeight - 5 + Canvas.GetTop(componentWithFocus.ComponentCanvas); AddChannel(channelToConnect); Canvas.SetZIndex(channelToConnect.Line, Canvas.GetZIndex(channelToConnect.Line) + 1000); CommandObject co = new CommandObject("Delete", channelToConnect); undoStack.Push(co); redoStack.Clear(); channelToConnect = null; newChannelRibbonButton.IsChecked = false; componentContextMenuItemAddChannel.IsEnabled = true; componentContextMenuItemConnectChannel.IsEnabled = false; componentContextMenuItemDropChannel.IsEnabled = false; } else { MessageBox.Show(Properties.Resources.PortConnectingDatyTypeErrorFormat(outPort.PortDataType, ((inputPortType)componentWithFocus.PortsList[channelToConnect.target.port.id]).PortDataType), Properties.Resources.PortConnectingDatyTypeErrorHeader, MessageBoxButton.OK, MessageBoxImage.Error); channelToConnect.target.component.id = null; channelToConnect.target.port.id = null; } } }
/// <summary> /// Drop a channel from the component context menu. This function be used, if a channel was created, but should not be connected to the selected input port /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void ComponentContextMenuItemDrop_Click(object sender, RoutedEventArgs e) { channelToConnect = null; newChannelRibbonButton.IsChecked = false; componentContextMenuItemAddChannel.IsEnabled = true; componentContextMenuItemConnectChannel.IsEnabled = false; componentContextMenuItemDropChannel.IsEnabled = false; }
/// <summary> /// Deselects all Channels and selects the given channel /// </summary> /// <param name="ch">Channel to select</param> private void ClearAndAddSelectedChannel(channel ch) { ClearSelectedChannelList(); if (!selectedChannelList.Contains(ch)) selectedChannelList.AddLast(ch); UpdateSelectedChannels(); }
/// <summary> /// A channel lost the focus /// </summary> /// <param name="sender"></param> /// <param name="args"></param> private void Channel_LostKeyboardFocus(object sender, RoutedEventArgs args) { ((Line)sender).StrokeDashArray = null; focusedChannel = null; //deleteChannelRibbonButton.IsEnabled = false; }
/// <summary> /// A channel got the focus, content in property dock will be reseted by ResetPropertyDock() /// </summary> /// <param name="sender"></param> /// <param name="args"></param> private void Channel_GotKeyboardFocus(object sender, RoutedEventArgs args) { DoubleCollection dashes = new DoubleCollection(); dashes.Add(1); dashes.Add(1); ((Line)sender).StrokeDashArray = dashes; //((Line)sender).Stroke = new SolidColorBrush(Colors.Red); //deleteChannelRibbonButton.IsEnabled = true; foreach (channel tempChannel in deploymentChannelList.Values) { if (tempChannel.Line == (Line)sender) { focusedChannel = tempChannel; break; } } ResetPropertyDock(); }
/// <summary> /// Additional select the given channel /// </summary> /// <param name="ch">Channel to select</param> private void AddSelectedChannel(channel ch) { if (!selectedChannelList.Contains(ch)) { selectedChannelList.AddLast(ch); if (ch.GroupOriginalSource != null) { foreach (channel c in deploymentChannelList.Values) { if (c.source.component.id.Equals(ch.GroupOriginalSource.component.id) && c.source.port.id.Equals(ch.GroupOriginalSource.port.id) && c.target.component.id.Equals(ch.target.component.id) && c.target.port.id.Equals(ch.target.port.id)) { AddSelectedChannel(c); } } } if (ch.GroupOriginalTarget != null) { foreach (channel c in deploymentChannelList.Values) { if (c.source.component.id.Equals(ch.source.component.id) && c.source.port.id.Equals(ch.source.port.id) && c.target.component.id.Equals(ch.GroupOriginalTarget.component.id) && c.target.port.id.Equals(ch.GroupOriginalTarget.port.id)) { AddSelectedChannel(c); } } } } UpdateSelectedChannels(); }
/// <summary> /// Hide the ports and the channel between the ports on the canvas /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void showPortsRibbonButton_Unchecked(object sender, RoutedEventArgs e) { // set visibility to "hidden" in the deploymentmodel foreach (componentType mc in deploymentModel.components) { if (mc != null && mc.ports != null) { foreach (object o in mc.ports) { if (o is outputPortType) { ((outputPortType)o).PortRectangle.Visibility = Visibility.Collapsed; ((outputPortType)o).PortLabel.Visibility = Visibility.Collapsed; } else if (o is inputPortType) { ((inputPortType)o).PortRectangle.Visibility = Visibility.Collapsed; ((inputPortType)o).PortLabel.Visibility = Visibility.Collapsed; } } } } // set visibility to "hidden" in the deploymentChannelList foreach (channel moc in deploymentChannelList.Values) { if (moc != null) { moc.Line.Visibility = Visibility.Collapsed; } } // set the ribbon buttons inactive newChannelRibbonButton.IsChecked = false; newChannelRibbonButton.IsEnabled = false; //deleteChannelRibbonButton.IsEnabled = false; if (channelToConnect != null) { canvas.Children.Remove(channelToConnect.Line); channelToConnect = null; } }