Investigating surface after Boolean op on Step solids

Technical discussions
Post Reply
Miguel Cantina
Posts: 1
Joined: Thu May 10, 2018 12:17 am

Investigating surface after Boolean op on Step solids

Post by Miguel Cantina »

Good day
Can you provide me the following sample in Delphi:
I can Load Object1 ( Step IGES or other )
I can load Object 2 ( Step IGes or other )
I can perform Boolean operation between both objects
I can determine the number of solid objects that resulted from the operation
I can save each individual output solid object in a file that I later can open with the initial load object

Also I would like to know how do I cycle in the boundaries of the solids ( its surfaces ) and how do I determine their connectivity, and how do I cycle in the boundaries of each surface and how do I cycle on each of those curves.
Thanks

Prashant Kande
Posts: 121
Joined: Mon Apr 04, 2016 4:55 am

Re: Investigating surface after Boolean op on Step solids

Post by Prashant Kande »

Hi Muguel

Here it is:
http://www.dynoinsight.com/Prod/Examples/BoolOpEx.zip

To see the functionality working in the sample debug it this way: File > Open dialog adds objects to the model. So after start open the A_*.step file in BoolOpExplorer folder. Then open B_*.step and press Execute (of Boolean Subtract).

Put break point into the TBoolOpForm.ExploreResult(). You will see how sub-shapes and structure of the resulting compound is analysed. You will see access to edges and surfaces there also

Here is the main code. It should be clear for non-Delphi people also:

Code: Select all

procedure TBoolOpForm.OnExecute(Sender: TObject);
var
iBoolSect: IBoolSection ;
_iBoolSectEx:		IBoolSectionEx;
iGener:				IDIObjGenerator;
context:		EBoolOpContext ;
_iArray: IArray;
operation: EBooleanOperation ;
iInterf : IInterFace;
iSectResult : ISection;
begin
  if( chOptionsIntersection.Checked Or radioOperationIntersCurve.Checked ) then
  begin
    // Case caclulation of intersection line is requested
		_iBoolSectEx := m_iSection0 as IBoolSectionEx;

		if( radioOperationIntersCurve.Checked ) then
		begin
			if(chOptionsAngles.Checked)  then
			begin
				iGener := m_iModel as IDIObjGenerator;
				iGener.Create( eObjTypeArray, iInterf);
         m_iArrayIntersection := iInterf as IArray;
			end;
			// Case only intersection line is required
			context.operation := eBoolOpSubtract;
			context.execute := false;			// Do not execute subtract, only intersection line
			context.intersectionLine :=	true;
			context.needEdges := chOptionsAngles.Checked;
      if( chOptionsAngles.Checked ) then 	context.edges := m_iArrayIntersection;
			context.separateComponents := false;

			_iBoolSectEx.Execute2( m_iSection1, context );

			// Render wire frame to show the calculated line
			KernelCAD1.RenderSolid := false;
		end
		else
		begin
			if(chOptionsAngles.Checked)  then _iArray := m_iArrayIntersection;

			operation := eBoolOpSubtract;

			if( radioOperationUnite.Checked ) then
      begin
				operation := eBoolOpUnion;
        end
			else if( radioOperationIntersect.Checked ) then
      begin
				operation := eBoolOpInters;
        end;

			_iBoolSectEx.Execute( operation, m_iSection1, true, _iArray );
		end;

		// Check that acces of points of the intersection line works
		DemonstrateIntersectionLineAccess();
  end
  else
  begin
    if(m_iSection0 = nil) then  UpdateFirstObjectInterface();

    iBoolSect := m_iSection0 as IBoolSection;

    if( radioOperationSubtract.Checked ) then
    begin
      iBoolSect.Subtract(m_iSection1);
    end
    else if( radioOperationUnite.Checked ) then
    begin
      iBoolSect.Unite(m_iSection1);

      // In case of union if surface is rendered it appears as ifnothing has changed. Show wire frame
      KernelCAD1.RenderSolid := false;
      chWireFrame.Checked := true;
    end
    else
    begin
      iBoolSect.Intersect(m_iSection1);
    end;
  end;

  // During the above operation the first object can be replaced with a new one
  // So the ISection interface is out of date and need to be updated when required
  m_iSection0 := Nil;

  m_iModel.GetSection(1, iSectResult);

  ExploreResult(iSectResult);

  radioModeView.Checked := true;

  KernelCAD1.UpdateView();

  UpdatePage();	// Enable the Show second object buton
end;

procedure TBoolOpForm.ExploreResult(iSectResult : ISection);
var
iInterf: IInterface;
iExplorerShape : IKO_TopExp_Explorer;
solids : IKO_TopTools_Array1OfShape;
shape : IKO_TopoDS_Shape;
i, size : Integer;
begin
  m_iGener.Create3('KO_BRep_Tool', iInterf);   m_iBRepTool:= iInterf as  IKO_BRep_Tool;

  iExplorerShape :=  iSectResult As  IKO_TopExp_Explorer;

  iExplorerShape.GetSubShapes(eShTop_SOLID, solids);
  solids.GetSize(size);

  for i:=1 to size do
		begin
      solids.GetValue(i, shape);
      ExploreSolid(shape);
    end;
end;

procedure TBoolOpForm.ExploreSolid(shape : IKO_TopoDS_Shape);
var
iExplorerShape : IKO_TopExp_Explorer;
shells : IKO_TopTools_Array1OfShape;
subShape : IKO_TopoDS_Shape;
i, size : Integer;
begin
  iExplorerShape :=  shape As  IKO_TopExp_Explorer;
  iExplorerShape.GetSubShapes(eShTop_SHELL, shells);
  shells.GetSize(size);

  for i:=1 to size do
		begin
      shells.GetValue(i, subShape);
      ExploreShell(subShape);
    end;
end;

procedure TBoolOpForm.ExploreShell(shape : IKO_TopoDS_Shape);
var
iExplorerShape : IKO_TopExp_Explorer;
shells : IKO_TopTools_Array1OfShape;
subShape : IKO_TopoDS_Shape;
i, size : Integer;
begin
  iExplorerShape :=  shape As  IKO_TopExp_Explorer;
  iExplorerShape.GetSubShapes(eShTop_FACE, shells);
  shells.GetSize(size);

  for i:=1 to size do
		begin
      shells.GetValue(i, subShape);
      ExploreFace(subShape);
    end;
end;

procedure TBoolOpForm.ExploreFace(shape : IKO_TopoDS_Shape);
var
iExplorerShape : IKO_TopExp_Explorer;
edges : IKO_TopTools_Array1OfShape;
vertices : IKO_TopTools_Array1OfShape;
vertex : IKO_TopoDS_Vertex;
subShape : IKO_TopoDS_Shape;
i, size : Integer;
face : IKO_TopoDS_Face;
surface : IKO_Geom_Surface;
u1, u2, v1, v2 : Double;
outPoint : DIPoint;
begin
  face :=  shape As IKO_TopoDS_Face;

  // Access surface geometry
  m_iBRepTool.Surface2(face, surface);
	// Get point in center of the face
	surface.Bounds(u1, u2, v1, v2);
	surface.D0(0.5*(u1 + u2), 0.5*(v1 + v2), outPoint);

  // List Vertices
  iExplorerShape :=  shape As  IKO_TopExp_Explorer;
  iExplorerShape.GetSubShapes(eShTop_VERTEX, vertices);
  vertices.GetSize(size);

  for i:=1 to size do
		begin
      vertices.GetValue(i, subShape);
      vertex := subShape As IKO_TopoDS_Vertex;
      m_iBRepTool.Pnt(vertex, outPoint);        // Coordinates
    end;

  // List edges
  iExplorerShape.GetSubShapes(eShTop_EDGE, edges);
  edges.GetSize(size);

  for i:=1 to size do
		begin
      edges.GetValue(i, subShape);
      ExploreEdge(subShape);
    end;
end;

procedure TBoolOpForm.ExploreEdge(shape : IKO_TopoDS_Shape);
var
edge : IKO_TopoDS_Edge;
iCurve : IKO_Geom_Curve;
first, last : Double;
P : DIPoint;
begin
  edge :=  shape As IKO_TopoDS_Edge;
  m_iBRepTool.Curve2(edge, first, last, iCurve);
  iCurve.D0(0.5*(first + last), P);
end;

Post Reply