public static void LinkDuplicates(I3dWorldObject self, SM3DWorldScene.DuplicationInfo duplicationInfo, bool allowLinkCopyToOrignal) { if (self.Links != null) { bool self_isCopy = duplicationInfo.IsDuplicate(self); bool self_hasCopy = duplicationInfo.HasDuplicate(self); foreach (var(linkName, link) in self.Links) { I3dWorldObject[] oldLink = link.ToArray(); //Clear Link link.Clear(); //Populate Link foreach (I3dWorldObject linked in oldLink) { bool linked_hasCopy = duplicationInfo.TryGetDuplicate(linked, out I3dWorldObject linked_copy); if (self_isCopy) { if (linked_hasCopy) { //link copy to copy link.Add(linked_copy); } else if (allowLinkCopyToOrignal) { //link copy to original link.Add(linked); } } else //self is original { if (linked_hasCopy && !self_hasCopy) { //link original to original and copy link.Add(linked); link.Add(linked_copy); } else { //link original to original link.Add(linked); } } } } } }
private void ChangeSelectedConnection(I3dWorldObject newSource, I3dWorldObject newDest, string newName) { if (newSource == SelectedConnection.Source && newDest == SelectedConnection.Dest && newName == SelectedConnection.Name) { return; //nothing has changed } if (newSource == newDest) { return; //a link can't load to itself } if (newName == "") { return; //a links name can't be empty } if (newSource is Rail) { return; //Rails can't have links } AddToUndo(new RevertableConnectionChange( newSource, newDest, newName, SelectedConnection.Source, SelectedConnection.Dest, SelectedConnection.Name )); RemoveConnection( SelectedConnection.Source, SelectedConnection.Dest, SelectedConnection.Name ); AddConnection(newSource, newDest, newName); UpdateLinkDestinations(); SelectedConnection = new LinkConnection(newSource, newDest, newName); }
public DestinationChangedEventArgs(I3dWorldObject linkDestination, bool destWasMovedToLinked) { LinkDestination = linkDestination; DestWasMovedToLinked = destWasMovedToLinked; }
/// <summary> /// Parses a 3d World from an ArrayEntry /// </summary> /// <param name="objectEntry"></param> /// <param name="zone"></param> /// <param name="objectsByReference"></param> /// <returns></returns> public static I3dWorldObject ParseObject(ArrayEntry objectEntry, SM3DWorldZone zone, Dictionary <long, I3dWorldObject> objectsByReference, out bool alreadyInLinks, Dictionary <string, I3dWorldObject> linkedObjsByID, bool isLinked = false) { ObjectInfo info = GetObjectInfo(ref objectEntry, zone); I3dWorldObject obj; bool loadLinks; if ((info.ClassName == "Area") || info.ObjectName.Contains("Area") && AreaModelNames.Contains(info.ModelName)) { obj = new AreaObject(in info, zone, out loadLinks); } else if (info.PropertyEntries.TryGetValue("RailPoints", out DictionaryEntry railPointEntry) && railPointEntry.NodeType == ByamlFile.ByamlNodeType.Array) //at this point we can be sure it's a rail { obj = new Rail(in info, zone, out loadLinks); } else { obj = new General3dWorldObject(in info, zone, out loadLinks); } if (isLinked && linkedObjsByID != null) { if (!linkedObjsByID.ContainsKey(info.ID)) { linkedObjsByID.Add(info.ID, obj); } else { alreadyInLinks = true; obj = linkedObjsByID[info.ID]; if (!isLinked) { alreadyInLinks = !zone.LinkedObjects.Remove(obj); } //in case this object was already read in another file if (!objectsByReference.ContainsKey(objectEntry.Position)) { objectsByReference.Add(objectEntry.Position, obj); } return(obj); } } alreadyInLinks = false; if (!objectsByReference.ContainsKey(objectEntry.Position)) { objectsByReference.Add(objectEntry.Position, obj); } else if (!isLinked) { obj = objectsByReference[objectEntry.Position]; zone.LinkedObjects.Remove(obj); return(obj); } if (loadLinks) { var links = new Dictionary <string, List <I3dWorldObject> >(); foreach (DictionaryEntry link in info.LinkEntries.Values) { links.Add(link.Key, new List <I3dWorldObject>()); foreach (ArrayEntry linked in link.IterArray()) { if (objectsByReference.ContainsKey(linked.Position)) { links[link.Key].Add(objectsByReference[linked.Position]); objectsByReference[linked.Position].AddLinkDestination(link.Key, obj); } else { I3dWorldObject _obj = ParseObject(linked, zone, objectsByReference, out bool linkedAlreadyReferenced, linkedObjsByID, true); _obj.AddLinkDestination(link.Key, obj); links[link.Key].Add(_obj); if (zone != null && !linkedAlreadyReferenced) { zone.LinkedObjects.Add(_obj); } } } } if (links.Count > 0) { obj.Links = links; } } return(obj); }
/// <summary> /// Parses a 3d World from an ArrayEntry /// </summary> /// <param name="objectEntry"></param> /// <param name="zone"></param> /// <param name="objectsByReference"></param> /// <returns></returns> public static I3dWorldObject ParseObject(ArrayEntry objectEntry, SM3DWorldZone zone, Dictionary <long, I3dWorldObject> objectsByReference, out bool alreadyInLinks, Dictionary <string, I3dWorldObject> linkedObjsByID, bool isLinked = false) { ObjectInfo info = GetObjectInfo(ref objectEntry, zone); I3dWorldObject obj; bool loadLinks; if (Enum.GetNames(typeof(Rail.RailObjType)).Contains(info.ClassName)) { obj = new Rail(info, zone, out loadLinks); } else { obj = new General3dWorldObject(info, zone, out loadLinks); } if (linkedObjsByID != null && isLinked) { if (!linkedObjsByID.ContainsKey(info.ID)) { linkedObjsByID.Add(info.ID, obj); } else { alreadyInLinks = true; obj = linkedObjsByID[info.ID]; if (!isLinked) { alreadyInLinks = !zone.LinkedObjects.Remove(obj); } //in case this object was already read in another file if (!objectsByReference.ContainsKey(objectEntry.Position)) { objectsByReference.Add(objectEntry.Position, obj); } return(obj); } } alreadyInLinks = false; if (!objectsByReference.ContainsKey(objectEntry.Position)) { objectsByReference.Add(objectEntry.Position, obj); } else if (!isLinked) { obj = objectsByReference[objectEntry.Position]; zone.LinkedObjects.Remove(obj); return(obj); } if (loadLinks) { obj.Links = new Dictionary <string, List <I3dWorldObject> >(); foreach (DictionaryEntry link in info.LinkEntries.Values) { obj.Links.Add(link.Key, new List <I3dWorldObject>()); foreach (ArrayEntry linked in link.IterArray()) { if (objectsByReference.ContainsKey(linked.Position)) { obj.Links[link.Key].Add(objectsByReference[linked.Position]); objectsByReference[linked.Position].AddLinkDestination(link.Key, obj); } else { I3dWorldObject _obj = ParseObject(linked, zone, objectsByReference, out bool linkedAlreadyReferenced, linkedObjsByID, true); _obj.AddLinkDestination(link.Key, obj); obj.Links[link.Key].Add(_obj); if (zone != null && !linkedAlreadyReferenced) { zone.LinkedObjects.Add(_obj); } } } } if (obj.Links.Count == 0) { obj.Links = null; } } return(obj); }
public DeleteInfo(int index, I3dWorldObject obj) { this.index = index; this.obj = obj; }
public LinkDestinationsUIContainer(I3dWorldObject obj, SM3DWorldScene scene) { this.obj = obj; this.scene = scene; }
public LinksUIContainer(I3dWorldObject obj, EditorSceneBase scene) { this.obj = obj; this.scene = scene; }