/// <summary> /// Searches for the destination at the end of the processing path. /// </summary> /// <param name="path">The processing path to trace.</param> /// <returns>Material destination</returns> private MaterialDestination SearchForDestination(ProcessingPath path) { // Does the processing trace have any history to trace ? if (this.Root == null) { return(null); } // Is there a processing path to trace ? if not then create an empty path to trace. if (path == null) { path = new ProcessingPath(); } if (path.Tag == null) { path.Tag = new ProcessingTag[0]; } // Search the processing tree for the destination associated with the processing path SearchForPathDetails finalSearch = SearchForPath(new SearchForPathDetails(path, 0, this.Root, new List <Procedure>())); //Debug.Assert(finalSearch != null); //Debug.Assert(path.Tag != null); return(finalSearch == null || finalSearch.tagLevel != path.Tag.Length ? null : finalSearch.destination); }
/// <summary> /// Gets the processing history associated with a processing path. /// </summary> /// <param name="processingPath">The processing path.</param> /// <returns></returns> internal ADX4.Process GetProcessingHistory(ProcessingPath processingPath) { // Does this processing tree have a root ? if not then there is not history to return. if (this.Root == null) { return(null); } // If the processing path is null then create an empty processing path to trace. if (processingPath == null) { processingPath = new ProcessingPath(); processingPath.Tag = new ProcessingTag[0]; } // Trace the processing path and build the list of procedures on it SearchForPathDetails finalSearch = SearchForPath(new SearchForPathDetails(processingPath, 0, this.Root, new List <Procedure>())); if (finalSearch == null || (finalSearch.tagLevel < processingPath.Tag.Length)) { this.OnValidationEvent(new ValidationResult(ErrorCodes.SampleProcessingHistory, ErrorLevel.Error, String.Format(Languages.Strings.valResultPathNotFoundInProcessingHistory, processingPath.ToString(), this.SampleRefs[0].IdRef))); return(null); } // Return the list of procedures for this processing path Process history = new Process(); history.Destination = new MaterialDestination(); history.Destination.Target = new MaterialTarget(); history.Destination.Target.Procedure = finalSearch.procedures.ToArray(); return(history); }
/// <summary> /// Searches for the end of the processing path. /// </summary> /// <param name="searchLevel">The search level within the processing path.</param> /// <returns>Position at the end of the processing path</returns> private SearchForPathDetails SearchForPath(SearchForPathDetails searchLevel) { // Has the search passed the end of the length of the processing path ? i.e. the path has 5 tags so we only need to search 5 tags into the processing tree Debug.Assert(searchLevel != null); Debug.Assert(searchLevel.path != null); Debug.Assert(searchLevel.path.Tag != null); if (searchLevel.tagLevel > searchLevel.path.Tag.Length) { return(searchLevel); } // Does the current search point have a target? or have we reached the end of a branch (and must stop searching whether we have compleed the processing path or not) if (searchLevel.destination == null || searchLevel.destination.Target == null || searchLevel.destination.Target.Procedure == null || searchLevel.destination.Target.Procedure.Length == 0) { searchLevel.endOfBranch = true; return(searchLevel); } // Add the current search destination's procedures to the cummulative list of procedures for (Int32 i = 0; i < searchLevel.destination.Target.Procedure.Length; i++) { searchLevel.procedures.Add(searchLevel.destination.Target.Procedure[i]); } // Get the destinations on the last procedure (we will continue searching along one of these destinations). List <MaterialDestination> destinations = searchLevel.destination.Target.Procedure[searchLevel.destination.Target.Procedure.Length - 1].GetDestinations(); // If we have not reached the end of the processing path then find the destination that matches the path and continue searching down that one. if (searchLevel.tagLevel < searchLevel.path.Tag.Length) { foreach (MaterialDestination destination in destinations) { if (searchLevel.path.Tag[searchLevel.tagLevel].Equals(destination.Name, destination.Type)) { return(SearchForPath(new SearchForPathDetails(searchLevel.path, searchLevel.tagLevel + 1, destination, searchLevel.procedures))); } } } // If there are multiple destinations and no destination was found to match the processing path then follow the first destination with an empty processing tag if (destinations.Count > 0) { // Is the tag empty ? for (int i = 0; i < destinations.Count; i++) { if (String.IsNullOrEmpty(destinations[i].Name) && String.IsNullOrEmpty(destinations[i].Type)) { // Does this destination have a target to search ? if so then search down it. if (destinations[i].HasTarget || destinations.Count > 1) { return(SearchForPath(new SearchForPathDetails(searchLevel.path, searchLevel.tagLevel, destinations[i], searchLevel.procedures))); } // If not then we have reached the end of a branch and must stop searching else { searchLevel.endOfBranch = true; return(searchLevel); } } } } return(null); }