/// <summary>
/// Detect the obstructions of pipe and resolve them.
/// </summary>
/// <param name="pipe">Pipe to resolve</param>
private void Resolve(Pipe pipe)
{
// Get the centerline of pipe.
Line pipeLine = (pipe.Location as LocationCurve).Curve as Line;
// Calculate the intersection references with pipe's centerline.
List <ReferenceWithContext> obstructionRefArr = m_detector.Obstructions(pipeLine);
// Filter out the references, just allow Pipe, Beam, and Duct.
Filter(pipe, obstructionRefArr);
if (obstructionRefArr.Count == 0)
{
// There are no intersection found.
return;
}
// Calculate the direction of pipe's centerline.
Autodesk.Revit.DB.XYZ dir = pipeLine.GetEndPoint(1) - pipeLine.GetEndPoint(0);
// Build the sections from the intersection references.
List <Section> sections = Section.BuildSections(obstructionRefArr, dir.Normalize());
// Merge the neighbor sections if the distance of them is too close.
for (int i = sections.Count - 2; i >= 0; i--)
{
Autodesk.Revit.DB.XYZ detal = sections[i].End - sections[i + 1].Start;
if (detal.GetLength() < pipe.Diameter * 3)
{
sections[i].Refs.AddRange(sections[i + 1].Refs);
sections.RemoveAt(i + 1);
}
}
// Resolve the obstructions one by one.
foreach (Section sec in sections)
{
Resolve(pipe, sec);
}
// Connect the neighbor sections with pipe and elbow fittings.
//
for (int i = 1; i < sections.Count; i++)
{
// Get the end point from the previous section.
Autodesk.Revit.DB.XYZ start = sections[i - 1].End;
// Get the start point from the current section.
Autodesk.Revit.DB.XYZ end = sections[i].Start;
// Create a pipe between two neighbor section.
Pipe tmpPipe = m_rvtDoc.Create.NewPipe(start, end, pipe.PipeType);
// Copy pipe's parameters values to tmpPipe.
CopyParameters(pipe, tmpPipe);
// Create elbow fitting to connect previous section with tmpPipe.
Connector conn1 = FindConnector(sections[i - 1].Pipes[2], start);
Connector conn2 = FindConnector(tmpPipe, start);
FamilyInstance fi = m_rvtDoc.Create.NewElbowFitting(conn1, conn2);
// Create elbow fitting to connect current section with tmpPipe.
Connector conn3 = FindConnector(sections[i].Pipes[0], end);
Connector conn4 = FindConnector(tmpPipe, end);
FamilyInstance f2 = m_rvtDoc.Create.NewElbowFitting(conn3, conn4);
}
// Find two connectors which pipe's two ends connector connected to.
Connector startConn = FindConnectedTo(pipe, pipeLine.GetEndPoint(0));
Connector endConn = FindConnectedTo(pipe, pipeLine.GetEndPoint(1));
Pipe startPipe = null;
if (null != startConn)
{
// Create a pipe between pipe's start connector and pipe's start section.
startPipe = m_rvtDoc.Create.NewPipe(sections[0].Start, startConn, pipe.PipeType);
}
else
{
// Create a pipe between pipe's start point and pipe's start section.
startPipe = m_rvtDoc.Create.NewPipe(sections[0].Start, pipeLine.GetEndPoint(0), pipe.PipeType);
}
// Copy parameters from pipe to startPipe.
CopyParameters(pipe, startPipe);
// Connect the startPipe and first section with elbow fitting.
Connector connStart1 = FindConnector(startPipe, sections[0].Start);
Connector connStart2 = FindConnector(sections[0].Pipes[0], sections[0].Start);
FamilyInstance fii = m_rvtDoc.Create.NewElbowFitting(connStart1, connStart2);
Pipe endPipe = null;
int count = sections.Count;
if (null != endConn)
{
// Create a pipe between pipe's end connector and pipe's end section.
endPipe = m_rvtDoc.Create.NewPipe(sections[count - 1].End, endConn, pipe.PipeType);
}
else
{
// Create a pipe between pipe's end point and pipe's end section.
endPipe = m_rvtDoc.Create.NewPipe(sections[count - 1].End, pipeLine.GetEndPoint(1), pipe.PipeType);
}
// Copy parameters from pipe to endPipe.
CopyParameters(pipe, endPipe);
// Connect the endPipe and last section with elbow fitting.
Connector connEnd1 = FindConnector(endPipe, sections[count - 1].End);
Connector connEnd2 = FindConnector(sections[count - 1].Pipes[2], sections[count - 1].End);
FamilyInstance fiii = m_rvtDoc.Create.NewElbowFitting(connEnd1, connEnd2);
// Delete the pipe after resolved.
m_rvtDoc.Delete(pipe.Id);
}