public void CleanManifest() { if (CrewAssignmentDialog.Instance != null) { VesselCrewManifest originalVesselManifest = CrewAssignmentDialog.Instance.GetManifest(); IList <PartCrewManifest> partCrewManifests = originalVesselManifest.GetCrewableParts(); if (partCrewManifests != null && partCrewManifests.Count > 0) { PartCrewManifest partManifest = partCrewManifests[0]; foreach (ProtoCrewMember crewMember in partManifest.GetPartCrew()) { if (crewMember != null) { // Clean the root part partManifest.RemoveCrewFromSeat(partManifest.GetCrewSeat(crewMember)); } } if (CrewRandRSettings.Instance != null && CrewRandRSettings.Instance.AssignCrews) { partManifest.AddCrewToOpenSeats(CrewRandR.Instance.GetCrewForPart(partManifest.PartInfo.partPrefab, new List <ProtoCrewMember>(), true)); } } CrewAssignmentDialog.Instance.RefreshCrewLists(originalVesselManifest, true, true); } }
/// <summary> /// Copies crew assignments from the dialog to the ship construct. /// </summary> private void CopyCrew() { VesselCrewManifest dialogVessel = CurrentDialogContents; if (dialogVessel == null) { Logging.Error("No dialog manifest, can't copy"); return; } VesselCrewManifest currentVessel = ShipConstruction.ShipManifest; List <PartCrewManifest> dialogParts = dialogVessel.GetCrewableParts(); List <PartCrewManifest> currentParts = currentVessel.GetCrewableParts(); if (dialogParts.Count != currentParts.Count) { Logging.Error("Crew dialog has " + dialogParts.Count + " crewable parts, but vessel has only " + currentParts.Count + ". Can't copy."); return; } for (int partIndex = 0; partIndex < dialogParts.Count; ++partIndex) { PartCrewManifest dialogPart = dialogParts[partIndex]; PartCrewManifest currentPart = currentParts[partIndex]; ProtoCrewMember[] dialogCrew = dialogPart.GetPartCrew(); ProtoCrewMember[] currentCrew = currentPart.GetPartCrew(); if ((dialogPart.PartID != currentPart.PartID) || (dialogCrew.Length != currentCrew.Length)) { Logging.Error("Mismatched manifests at index " + partIndex + ", can't copy."); return; } for (int slotIndex = 0; slotIndex < dialogCrew.Length; ++slotIndex) { ProtoCrewMember dialogMember = dialogCrew[slotIndex]; ProtoCrewMember currentMember = currentCrew[slotIndex]; if (!AreSame(dialogMember, currentMember)) { Logging.Log("Crew change in " + currentPart.PartInfo.title + " slot " + slotIndex + ": " + DescribeCrew(currentMember) + " -> " + DescribeCrew(dialogMember)); currentPart.RemoveCrewFromSeat(slotIndex); if (dialogMember != null) { if (currentVessel.Contains(dialogMember)) { PartCrewManifest previousPart = currentVessel.GetPartForCrew(dialogMember); previousPart.RemoveCrewFromSeat(previousPart.GetCrewSeat(dialogMember)); } currentPart.AddCrewToSeat(dialogMember, slotIndex); } } // if there's an assignment difference } // for each slot in the part } // for each crewable part in the vessel }
/// <summary> /// Gets the crew slots for the specified part & manifest. /// </summary> /// <param name="part"></param> /// <param name="manifest"></param> /// <returns></returns> public static List <CrewSlot> GetSlots(Part part, PartCrewManifest manifest) { Assignment[] assignments = Assignment.GetSlotAssignments(part); int capacity = manifest.GetPartCrew().Length; if (assignments.Length != capacity) { throw new Exception("Mismatched capacity when making slots"); } List <CrewSlot> slots = new List <CrewSlot>(capacity); for (int index = 0; index < capacity; ++index) { slots.Add(new CrewSlot(assignments[index], manifest, index)); } return(slots); }
/// <summary> /// Copies crew assignments from the dialog to the ship construct. /// </summary> private void CopyCrew() { VesselCrewManifest dialogVessel = CurrentDialogContents; if (dialogVessel == null) { return; } VesselCrewManifest currentVessel = ShipConstruction.ShipManifest; List <PartCrewManifest> dialogParts = dialogVessel.GetCrewableParts(); List <PartCrewManifest> currentParts = currentVessel.GetCrewableParts(); if (dialogParts.Count != currentParts.Count) { return; } for (int partIndex = 0; partIndex < dialogParts.Count; ++partIndex) { PartCrewManifest dialogPart = dialogParts[partIndex]; PartCrewManifest currentPart = currentParts[partIndex]; ProtoCrewMember[] dialogCrew = dialogPart.GetPartCrew(); ProtoCrewMember[] currentCrew = currentPart.GetPartCrew(); if ((dialogPart.PartID != currentPart.PartID) || (dialogCrew.Length != currentCrew.Length)) { return; } for (int slotIndex = 0; slotIndex < dialogCrew.Length; ++slotIndex) { ProtoCrewMember dialogMember = dialogCrew[slotIndex]; ProtoCrewMember currentMember = currentCrew[slotIndex]; if (!AreSame(dialogMember, currentMember)) { currentPart.RemoveCrewFromSeat(slotIndex); if (dialogMember != null) { if (currentVessel.Contains(dialogMember)) { PartCrewManifest previousPart = currentVessel.GetPartForCrew(dialogMember); previousPart.RemoveCrewFromSeat(previousPart.GetCrewSeat(dialogMember)); } currentPart.AddCrewToSeat(dialogMember, slotIndex); } } // if there's an assignment difference } // for each slot in the part } // for each crewable part in the vessel }
/// <summary> /// Given a ship construct from the editor, get a list of crewables. Throws if /// there's an error. /// </summary> /// <param name="construct"></param> /// <returns></returns> public static List <Crewable> List(ShipConstruct construct) { // Get all the parts that are crewable List <Part> parts = new List <Part>(); foreach (Part part in construct.parts) { if (part.CrewCapacity > 0) { parts.Add(part); } } // Get all the crewable parts from the vessel manifest and hope like hell that they're in the same order List <PartCrewManifest> manifests = ShipConstruction.ShipManifest.GetCrewableParts(); if (parts.Count != manifests.Count) { throw new Exception("Mismatched lists: " + parts.Count + " crewable parts (out of " + construct.parts.Count + " total), " + manifests.Count + " part manifests"); } List <Crewable> crewables = new List <Crewable>(parts.Count); for (int index = 0; index < parts.Count; ++index) { Part part = parts[index]; PartCrewManifest manifest = manifests[index]; String partName = part.partInfo.name; String manifestName = manifest.PartInfo.name; if (!partName.Equals(manifestName)) { throw new Exception("Mismatch at index " + index + ": " + partName + " versus " + manifestName); } int partCapacity = part.CrewCapacity; int manifestCapacity = manifest.GetPartCrew().Length; if (partCapacity != manifestCapacity) { throw new Exception("Mismatched capacity for " + partName + ": " + partCapacity + " for part, " + manifestCapacity + " for manifest"); } crewables.Add(new Crewable(part, manifest, partCapacity)); } return(crewables); }
public static IEnumerable <ProtoCrewMember> AddCrewToOpenSeats(this PartCrewManifest crewManifest, IEnumerable <ProtoCrewMember> crewMembers) { // crewManifest.GetPartCrew() is a statically-sized array with null elements IEnumerable <int> openSeatIndexes = crewManifest.GetPartCrew().Select((x, index) => new { x, index }).Where(x => x.x == null).Select(x => x.index); // Need to know the number of excluded elements int openSeatIndexesCount = openSeatIndexes.ToArray().Length; // Get the members we are going to assign IEnumerator <ProtoCrewMember> crewEnumerator = crewMembers.Take(openSeatIndexesCount).GetEnumerator(); #if DEBUG Logging.Debug("indexLength:" + openSeatIndexes.ToArray().Length); foreach (int i in openSeatIndexes) { Logging.Debug("indexes:" + i); } foreach (ProtoCrewMember crew in crewMembers.Take(openSeatIndexesCount)) { Logging.Debug("crew:" + crew.name); } #endif foreach (int index in openSeatIndexes) { if (crewEnumerator.MoveNext()) { crewManifest.AddCrewToSeat(crewEnumerator.Current, index); } else { return(crewMembers.Skip(openSeatIndexesCount));; } } // return the remainders return(crewMembers.Skip(openSeatIndexesCount));; }
void ScaleCrewCapacity() { // scale crew capacity (balancing: conserve mass/kerbal) var cOld = part.CrewCapacity; var cNew = (int)(_prefabPart.CrewCapacity * MassScale); if (cOld == cNew) { Debug.Log("CrewCapacity: old=new=" + cNew.ToString()); return; } part.CrewCapacity = cNew; if (HighLogic.LoadedSceneIsFlight) { return; } var manifests = ShipConstruction.ShipManifest.GetCrewableParts(); PartCrewManifest crew = null; for (int i = 0; i < manifests.StupidCount(); i++) { if (manifests[i].PartID == part.craftID) { crew = manifests[i]; break; } } if (crew == null) { Tools.LogWf("No PartManifest found!"); return; } if (cOld != crew.GetPartCrew().Count()) { Debug.Log("Crew mismatch: part=" + cOld + ", crew=" + crew.GetPartCrew().Count().ToString()); } //else Debug.Log("Manifest found"); // clear seats (just for safety) for (int i = 0; i < crew.GetPartCrew().Count(); i++) { if (crew.GetPartCrew()[i] != null) { Debug.Log("Removing seat:" + i.ToString() + crew.GetPartCrew()[i].name); crew.RemoveCrewFromSeat(i); } } //Debug.Log("Cleared seats"); // close crew tab (otherwise it will not update correctly) if (EditorLogic.fetch.editorScreen == EditorScreen.Crew) { EditorLogic.fetch.SelectPanelParts(); } FieldInfo[] fields = typeof(PartCrewManifest).GetFields(BindingFlags.NonPublic | BindingFlags.Instance); foreach (FieldInfo f in fields) { if (f.Name == "partCrew") { f.SetValue(crew, new string[cNew]); } } ShipConstruction.ShipManifest.SetPartManifest(part.craftID, crew); }