0022666: EDF 7253 GEOM: Add thickness to a shell and integrate BrepOffsetAPI_MakeThickSolid

This commit is contained in:
skv 2015-03-16 17:23:18 +03:00
parent 1344a93905
commit fca24cf286
30 changed files with 923 additions and 87 deletions

View File

@ -67,6 +67,7 @@ SET(GOOD_TESTS
complex_objs_ex08.py
complex_objs_ex09.py
complex_objs_ex10.py
complex_objs_ex11.py
free_boundaries.py
free_faces.py
GEOM_box.py

View File

@ -0,0 +1,39 @@
# Apply thickness for shell
import salome
salome.salome_init()
import GEOM
from salome.geom import geomBuilder
geompy = geomBuilder.New(salome.myStudy)
gg = salome.ImportComponentGUI("GEOM")
# create box
box = geompy.MakeBoxDXDYDZ(100, 100, 100)
# get the list of faces
faces = geompy.SubShapeAllSortedCentres(box, geompy.ShapeType["FACE"])
# get the list of face IDs
faceIDs = geompy.SubShapeAllSortedCentresIDs(box, geompy.ShapeType["FACE"])
# make a shell from 3 faces
shell = geompy.MakeShell([faces[0], faces[1], faces[2]])
# apply thickness
solid = geompy.MakeThickSolid(shell, 30.)
# create box
hsolid = geompy.MakeBoxDXDYDZ(100, 100, 100)
# make hollowed solid
geompy.Thicken(hsolid, 30., [faceIDs[0], faceIDs[1]])
# add objects in the study
id_shell = geompy.addToStudy(shell, "Shell")
id_solid = geompy.addToStudy(solid, "Solid")
id_hsolid = geompy.addToStudy(hsolid, "Hollowed Solid")
# display the shell and the result thicknen solid and hollowed solid
gg.createAndDisplayGO(id_shell)
gg.createAndDisplayGO(id_solid)
gg.createAndDisplayGO(id_hsolid)

Binary file not shown.

After

Width:  |  Height:  |  Size: 22 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.9 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 24 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.4 KiB

View File

@ -15,6 +15,7 @@ axis, creating a body of revolution.</li>
<li>\subpage create_extrusion_alongpath_page "Extrude an object along a path",
creating a more complex trajectory object.</li>
<li>\subpage create_pipe_path_page "Restore Path" of a pipe-like shape.</li>
<li>\subpage create_thickness_page "Thickness" operation that allows to add a thickness to objects.</li>
</ul>
<b> New entity -> Advanced </b> sub-menu allows creating new geometric

View File

@ -0,0 +1,46 @@
/*!
\page create_thickness_page Thickness Construction
To add a \b Thickness to a shape in the <b>Main Menu</b> select <b>New Entity - > Generation - > Thickness</b>
\n
It is possible to create a Solid from a Face or a Shell by applying a
\b Thickness. To do it you should define an \b Object that is a Face or a
Shell, \b Thickness and to define the thickness direction by means of
<b>Thicken towards the inside</b> check box.
\image html thickness.png
<b>Example:</b>
\image html thickness_result.png "Thickness of Shell"
It is possible to apply \b Thickness to a Solid. The result of this operation
is the hollowed Solid. To do it you should define an \b Object that is a Solid,
\b Faces to be removed from result, \b Thickness and the thickness direction by
means of <b>Thicken towards the inside</b> check box.
\image html thicksolid.png
<b>Example:</b>
\image html thicksolid_result.png "Thickness of Solid"
\n <b>TUI Commands:</b>
\n
<em>geompy.MakeThickSolid(theShape, theThickness, theFacesIDs=[])</em> -
Makes a thick solid from a shape;
\n
<em>geompy.Thicken(theShape, theThickness, theFacesIDs=[])</em> -
Modifies a shape to make it a thick solid.
<b>Arguments:</b> Name + 1 shape (face, shell or solid) + thickness +
the list of face IDs.
\n If the shape is face or shell the list of face IDs is not used.
The thickness can be positive or negative for thicken towards the inside.
\n\n <b>Advanced options</b> \ref preview_anchor "Preview"
Our <b>TUI Scripts</b> provide you with useful examples of creation of
\ref tui_creation_thickness "Complex Geometric Objects".
*/

View File

@ -42,4 +42,8 @@
<br><h2>Creation of Tangent Plane On Face</h2>
\tui_script{complex_objs_ex10.py}
\anchor tui_creation_thickness
<br><h2>Applying a Thickness to Face, Shell or Solid</h2>
\tui_script{complex_objs_ex11.py}
*/

View File

@ -1829,14 +1829,22 @@ module GEOM
/*!
* \brief Make a thick solid from a surface shape (face or shell)
* \param theObject Surface from which the thick solid is made
* \brief Make a thick solid from a shape.
*
* If the input is a surface shape (face or shell) the result is
* a thick solid. If an input shape is a solid the result is a hollowed
* solid with removed faces.
* \param theObject face or shell to get thick solid or solid to get
* hollowed solid.
* \param theFacesIDs the list of face IDs to be removed from the result.
* It can be empty.
* \param theThickness Value of the thickness
* \param isCopy To make a copy of \a theObject ot to modify \a theObject.
* \param isCopy To make a copy of \a theObject or to modify \a theObject
* \return New GEOM_Object, containing the created pipe if isCopy = true
* or the modified object if isCopy = false
*/
GEOM_Object MakeThickening (in GEOM_Object theObject,
in ListOfLong theFacesIDs,
in double theThickness,
in boolean isCopy);

View File

@ -180,6 +180,8 @@ SET( _res_files
supressHolesOnFaceShell.png
supressface.png
supresshole.png
thickness.png
thickness2.png
tolerance.png
torus.png
torusdxyz.png

BIN
resources/thickness.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 471 B

BIN
resources/thickness2.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 798 B

View File

@ -555,6 +555,14 @@
<source>ICON_DLG_PRISM_DXDYDZ</source>
<translation>prism3.png</translation>
</message>
<message>
<source>ICON_DLG_THICKNESS</source>
<translation>thickness.png</translation>
</message>
<message>
<source>ICON_DLG_THICKNESS_HOLLOWED</source>
<translation>thickness2.png</translation>
</message>
<message>
<source>ICON_DLG_PROPAGATE</source>
<translation>propagate.png</translation>
@ -1011,6 +1019,10 @@
<source>ICO_EXTRUSION</source>
<translation>prism.png</translation>
</message>
<message>
<source>ICO_THICKNESS</source>
<translation>thickness.png</translation>
</message>
<message>
<source>ICO_FACE</source>
<translation>build_face.png</translation>

View File

@ -675,6 +675,18 @@ Please, select face, shell or solid and try again</translation>
<source>GEOM_EXTRUSION_TITLE</source>
<translation>Construction by Extrusion</translation>
</message>
<message>
<source>GEOM_THICKNESS_TITLE</source>
<translation>Thickness Construction</translation>
</message>
<message>
<source>GEOM_THICKNESS_NAME</source>
<translation>Thickness</translation>
</message>
<message>
<source>GEOM_TOWARDS_INSIDE</source>
<translation>Thicken towards the inside</translation>
</message>
<message>
<source>GEOM_SCALE_PRISM</source>
<translation>Scale the face opposite to the base</translation>
@ -2852,6 +2864,10 @@ Please, select face, shell or solid and try again</translation>
<source>MEN_PIPE_PATH</source>
<translation>Restore Path</translation>
</message>
<message>
<source>MEN_THICKNESS</source>
<translation>Thickness</translation>
</message>
<message>
<source>MEN_PLANE</source>
<translation>Plane</translation>
@ -3800,6 +3816,10 @@ Please, select face, shell or solid and try again</translation>
<source>STB_PIPE_PATH</source>
<translation>Restore path from a pipe-like shape</translation>
</message>
<message>
<source>STB_THICKNESS</source>
<translation>Make a thick solid</translation>
</message>
<message>
<source>STB_PLANE</source>
<translation>Create a plane</translation>
@ -4416,6 +4436,10 @@ Please, select face, shell or solid and try again</translation>
<source>TOP_PIPE_PATH</source>
<translation>Restore path</translation>
</message>
<message>
<source>TOP_THICKNESS</source>
<translation>Thickness</translation>
</message>
<message>
<source>TOP_PLANE</source>
<translation>Create a plane</translation>
@ -6039,10 +6063,6 @@ Number of sketch points too small</translation>
<source>GEOM_ADD_THICKNESS</source>
<translation>Add thickness (edges or wires only)</translation>
</message>
<message>
<source>GEOM_TOWARDS_INSIDE</source>
<translation>Thicken towards the inside</translation>
</message>
</context>
<context>
<name>GroupGUI</name>

View File

@ -548,6 +548,7 @@ void GeometryGUI::OnGUIEvent( int id, const QVariant& theParam )
case GEOMOp::OpFilling: // MENU GENERATION - FILLING
case GEOMOp::OpPipe: // MENU GENERATION - PIPE
case GEOMOp::OpPipePath: // MENU GENERATION - RESTORE PATH
case GEOMOp::OpThickness: // MENU GENERATION - THICKNESS
libName = "GenerationGUI";
break;
case GEOMOp::Op2dSketcher: // MENU ENTITY - SKETCHER
@ -921,6 +922,7 @@ void GeometryGUI::initialize( CAM_Application* app )
createGeomAction( GEOMOp::OpFilling, "FILLING" );
createGeomAction( GEOMOp::OpPipe, "PIPE" );
createGeomAction( GEOMOp::OpPipePath, "PIPE_PATH" );
createGeomAction( GEOMOp::OpThickness, "THICKNESS" );
createGeomAction( GEOMOp::OpGroupCreate, "GROUP_CREATE" );
createGeomAction( GEOMOp::OpGroupEdit, "GROUP_EDIT" );
@ -1144,6 +1146,7 @@ void GeometryGUI::initialize( CAM_Application* app )
createMenu( GEOMOp::OpFilling, genId, -1 );
createMenu( GEOMOp::OpPipe, genId, -1 );
createMenu( GEOMOp::OpPipePath, genId, -1 );
createMenu( GEOMOp::OpThickness, genId, -1 );
//int advId = createMenu( tr( "MEN_ADVANCED" ), newEntId, -1 );
//createMenu( GEOMOp::OpSmoothingSurface, advId, -1 );
@ -1372,6 +1375,7 @@ void GeometryGUI::initialize( CAM_Application* app )
createTool( GEOMOp::OpFilling, genTbId );
createTool( GEOMOp::OpPipe, genTbId );
createTool( GEOMOp::OpPipePath, genTbId );
createTool( GEOMOp::OpThickness, genTbId );
int transTbId = createTool( tr( "TOOL_TRANSFORMATION" ), QString( "GEOMTransformation" ) );
createTool( GEOMOp::OpTranslate, transTbId );

View File

@ -111,6 +111,7 @@ namespace GEOMOp {
OpFilling = 3202, // MENU NEW ENTITY - GENERATION - FILLING
OpPipe = 3203, // MENU NEW ENTITY - GENERATION - EXTRUSION ALONG PATH
OpPipePath = 3204, // MENU NEW ENTITY - GENERATION - RESTORE PATH
OpThickness = 3205, // MENU NEW ENTITY - GENERATION - THICKNESS
// EntityGUI -------------------//--------------------------------
Op2dSketcher = 3300, // MENU NEW ENTITY - SKETCHER
Op3dSketcher = 3301, // MENU NEW ENTITY - 3D SKETCHER

View File

@ -2287,9 +2287,11 @@ Handle(GEOM_Object) GEOMImpl_I3DPrimOperations::MakePipeBiNormalAlongVector (Han
* MakeThickening
*/
//=============================================================================
Handle(GEOM_Object) GEOMImpl_I3DPrimOperations::MakeThickening(Handle(GEOM_Object) theObject,
Handle(GEOM_Object) GEOMImpl_I3DPrimOperations::MakeThickening
(Handle(GEOM_Object) theObject,
const Handle(TColStd_HArray1OfInteger) &theFacesIDs,
double theOffset,
bool copy = true)
bool isCopy)
{
SetErrorCode(KO);
@ -2301,7 +2303,7 @@ Handle(GEOM_Object) GEOMImpl_I3DPrimOperations::MakeThickening(Handle(GEOM_Objec
//Add a new Offset function
Handle(GEOM_Function) aFunction;
Handle(GEOM_Object) aCopy;
if (copy)
if (isCopy)
{
//Add a new Copy object
aCopy = GetEngine()->AddObject(GetDocID(), theObject->GetType());
@ -2319,6 +2321,10 @@ Handle(GEOM_Object) GEOMImpl_I3DPrimOperations::MakeThickening(Handle(GEOM_Objec
aTI.SetShape(anOriginal);
aTI.SetValue(theOffset);
if (theFacesIDs.IsNull() == Standard_False) {
aTI.SetFaceIDs(theFacesIDs);
}
//Compute the offset
try {
OCC_CATCH_SIGNALS;
@ -2334,20 +2340,36 @@ Handle(GEOM_Object) GEOMImpl_I3DPrimOperations::MakeThickening(Handle(GEOM_Objec
}
//Make a Python command
if(copy)
{
GEOM::TPythonDump(aFunction) << aCopy << " = geompy.MakeThickSolid("
<< theObject << ", " << theOffset << ")";
SetErrorCode(OK);
return aCopy;
GEOM::TPythonDump pd (aFunction);
Handle(GEOM_Object) aResult;
if (isCopy) {
pd << aCopy << " = geompy.MakeThickSolid("
<< theObject << ", " << theOffset;
aResult = aCopy;
} else {
pd << "geompy.Thicken(" << theObject << ", " << theOffset;
aResult = theObject;
}
else
{
GEOM::TPythonDump(aFunction) << "geompy.Thicken("
<< theObject << ", " << theOffset << ")";
SetErrorCode(OK);
return theObject;
if (theFacesIDs.IsNull() == Standard_False) {
// Dump faces IDs.
Standard_Integer i;
pd << ", [";
for (i = theFacesIDs->Lower(); i < theFacesIDs->Upper(); ++i) {
pd << theFacesIDs->Value(i) << ", ";
}
// Dump the last value.
pd << theFacesIDs->Value(i) << "]";
}
pd << ")";
SetErrorCode(OK);
return aResult;
}
//=============================================================================

View File

@ -144,7 +144,9 @@ class GEOMImpl_I3DPrimOperations : public GEOM_IOperations {
Handle(GEOM_Object) thePath,
Handle(GEOM_Object) theVec);
Standard_EXPORT Handle(GEOM_Object) MakeThickening (Handle(GEOM_Object) theObject,
Standard_EXPORT Handle(GEOM_Object) MakeThickening
(Handle(GEOM_Object) theObject,
const Handle(TColStd_HArray1OfInteger) &theFacesIDs,
double theOffset,
bool isCopy);

View File

@ -23,9 +23,11 @@
//NOTE: This is an intreface to a function for the Offset creation.
//
#include "GEOM_Function.hxx"
#include <TColStd_HArray1OfInteger.hxx>
#define OFF_ARG_SHAPE 1
#define OFF_ARG_VALUE 2
#define OFF_ARG_IDS 3
class GEOMImpl_IOffset
{
@ -41,6 +43,12 @@ class GEOMImpl_IOffset
double GetValue() { return _func->GetReal(OFF_ARG_VALUE); }
void SetFaceIDs(const Handle(TColStd_HArray1OfInteger)& theFaceIDs)
{ _func->SetIntegerArray(OFF_ARG_IDS, theFaceIDs); }
Handle(TColStd_HArray1OfInteger) GetFaceIDs()
{ return _func->GetIntegerArray(OFF_ARG_IDS); }
private:
Handle(GEOM_Function) _func;

View File

@ -29,8 +29,10 @@
#include <GEOMUtils.hxx>
#include <BRepOffsetAPI_MakeOffsetShape.hxx>
#include <BRepOffsetAPI_MakeThickSolid.hxx>
#include <TopoDS_Shape.hxx>
#include <TopAbs.hxx>
#include <TopExp.hxx>
#include <BRepClass3d_SolidClassifier.hxx>
#include <Precision.hxx>
#include <Standard_ConstructionError.hxx>
@ -95,6 +97,10 @@ Standard_Integer GEOMImpl_OffsetDriver::Execute(TFunction_Logbook& log) const
}
else if (aType == OFFSET_THICKENING || aType == OFFSET_THICKENING_COPY)
{
const TopAbs_ShapeEnum aType = aShapeBase.ShapeType();
if (aType == TopAbs_FACE || aType == TopAbs_SHELL) {
// Create a thick solid.
BRepClass3d_SolidClassifier aClassifier = BRepClass3d_SolidClassifier(aShapeBase);
aClassifier.PerformInfinitePoint(Precision::Confusion());
if (aClassifier.State()==TopAbs_IN)
@ -121,6 +127,49 @@ Standard_Integer GEOMImpl_OffsetDriver::Execute(TFunction_Logbook& log) const
{
aShape.Reverse();
}
} else if (aType == TopAbs_SOLID) {
// Create a hollowed solid.
Handle(TColStd_HArray1OfInteger) aFacesIDs = aCI.GetFaceIDs();
TopTools_ListOfShape aFacesToRm;
if (aFacesIDs.IsNull()) {
return 0;
}
TopTools_IndexedMapOfShape anIndices;
TopExp::MapShapes(aShapeBase, anIndices);
Standard_Integer aNbShapes = anIndices.Extent();
Standard_Integer i;
for (i = aFacesIDs->Lower(); i <= aFacesIDs->Upper(); ++i) {
const Standard_Integer anIndex = aFacesIDs->Value(i);
if (anIndex < 1 || anIndex > aNbShapes) {
// Invalid index.
return 0;
}
const TopoDS_Shape &aFace = anIndices.FindKey(anIndex);
if (aFace.ShapeType() != TopAbs_FACE) {
// Shape by index is not a face.
return 0;
}
aFacesToRm.Append(aFace);
}
// Create a hollowed solid.
BRepOffsetAPI_MakeThickSolid aMkSolid
(aShapeBase, aFacesToRm, anOffset, aTol, BRepOffset_Skin,
Standard_False, Standard_False, GeomAbs_Intersection);
if (aMkSolid.IsDone()) {
aShape = aMkSolid.Shape();
}
}
}
if (aShape.IsNull()) return 0;
@ -160,6 +209,13 @@ GetCreationInformation(std::string& theOperationName,
theOperationName = "MakeThickening";
AddParam( theParams, "Object", aCI.GetShape() );
AddParam( theParams, "Offset", aCI.GetValue() );
{
Handle(TColStd_HArray1OfInteger) aFacesIDs = aCI.GetFaceIDs();
if (aFacesIDs.IsNull() == Standard_False) {
AddParam(theParams, "Faces IDs", aFacesIDs);
}
}
break;
default:
return false;

View File

@ -1185,6 +1185,7 @@ GEOM::GEOM_Object_ptr GEOM_I3DPrimOperations_i::MakePipeBiNormalAlongVector
//=============================================================================
GEOM::GEOM_Object_ptr GEOM_I3DPrimOperations_i::MakeThickening
(GEOM::GEOM_Object_ptr theObject,
const GEOM::ListOfLong &theFacesIDs,
CORBA::Double theOffset,
CORBA::Boolean doCopy)
{
@ -1207,11 +1208,24 @@ GEOM::GEOM_Object_ptr GEOM_I3DPrimOperations_i::MakeThickening
Handle(GEOM_Object) aBasicObject = GetObjectImpl(theObject);
if (aBasicObject.IsNull()) return aGEOMObject._retn();
// Get faces IDs.
Handle(TColStd_HArray1OfInteger) aFaceIDs;
Standard_Integer aNbIDs = theFacesIDs.length();
Standard_Integer i;
if (aNbIDs > 0) {
aFaceIDs = new TColStd_HArray1OfInteger (1, aNbIDs);
for (i = 0; i < aNbIDs; i++) {
aFaceIDs->SetValue(i + 1, theFacesIDs[i]);
}
}
//Create the thickened shape
if (doCopy)
{
Handle(GEOM_Object) anObject = GetOperations()->MakeThickening(
aBasicObject, theOffset, doCopy);
aBasicObject, aFaceIDs, theOffset, doCopy);
if (!GetOperations()->IsDone() || anObject.IsNull())
return aGEOMObject._retn();
@ -1219,7 +1233,7 @@ GEOM::GEOM_Object_ptr GEOM_I3DPrimOperations_i::MakeThickening
}
else
{
GetOperations()->MakeThickening(aBasicObject, theOffset, doCopy);
GetOperations()->MakeThickening(aBasicObject, aFaceIDs, theOffset, doCopy);
// Update GUI.
UpdateGUIForObject(theObject);

View File

@ -199,6 +199,7 @@ class GEOM_I_EXPORT GEOM_I3DPrimOperations_i :
GEOM::GEOM_Object_ptr theVec);
GEOM::GEOM_Object_ptr MakeThickening (GEOM::GEOM_Object_ptr theObject,
const GEOM::ListOfLong &theFacesIDs,
CORBA::Double theOffset,
CORBA::Boolean isCopy);

View File

@ -242,6 +242,13 @@ def TestAll (geompy, math):
Pipe = geompy.MakePipe(Wire, Edge) #(2 GEOM_Object)->GEOM_Object
Sewing = geompy.MakeSewing([Face, S], precision) #(List Of GEOM_Object, Double)->GEOM_Object
Copy = geompy.MakeCopy(Box) #(GEOM_Object)->GEOM_Object
ThickSolid = geompy.MakeCopy(Box)
faces = geompy.SubShapeAllSortedCentres(Box, geompy.ShapeType["FACE"])
shell = geompy.MakeShell([faces[0], faces[1], faces[2]])
faceIDs = geompy.SubShapeAllSortedCentresIDs(
ThickSolid, geompy.ShapeType["FACE"])
ThickShell = geompy.MakeThickSolid(shell, 50) #(GEOM_Object, Double)->GEOM_Object
geompy.Thicken(ThickSolid, 50, [faceIDs[0], faceIDs[1]]) #(GEOM_Object) modification
#Transform objects
Translation = geompy.MakeTranslationTwoPoints(Box, px, pz) #(3 GEOM_Object)->GEOM_Object
@ -437,6 +444,9 @@ def TestAll (geompy, math):
id_Plane2 = geompy.addToStudy(Plane2, "Plane on Face")
id_Copy = geompy.addToStudy(Copy, "Copy")
id_ThickShell = geompy.addToStudy(ThickShell, "ThickShell")
id_ThickSolid = geompy.addToStudy(ThickSolid, "ThickSolid")
id_Prism = geompy.addToStudy(Prism, "Prism")
id_Prism2Ways = geompy.addToStudy(Prism2Ways, "Prism2Ways")
id_PrismTwoPnt = geompy.addToStudy(PrismTwoPnt, "PrismTwoPnt")

65
src/GEOM_SWIG/geomBuilder.py Executable file → Normal file
View File

@ -4140,23 +4140,37 @@ class geomBuilder(object, GEOM._objref_GEOM_Gen):
self._autoPublish(anObj, theName, "pipe")
return anObj
## Makes a thick solid from a face or a shell
# @param theShape Face or Shell to be thicken
## Makes a thick solid from a shape. If the input is a surface shape
# (face or shell) the result is a thick solid. If an input shape is
# a solid the result is a hollowed solid with removed faces.
# @param theShape Face or Shell to get thick solid or solid to get
# hollowed solid.
# @param theThickness Thickness of the resulting solid
# @param theFacesIDs the list of face IDs to be removed from the
# result. It is ignored if \a theShape is a face or a shell.
# It is empty by default.
# @param theName Object name; when specified, this parameter is used
# for result publication in the study. Otherwise, if automatic
# publication is switched on, default value is used for result name.
#
# @return New GEOM.GEOM_Object, containing the created solid
#
# @ref tui_creation_thickness "Example"
@ManageTransactions("PrimOp")
def MakeThickSolid(self, theShape, theThickness, theName=None):
def MakeThickSolid(self, theShape, theThickness,
theFacesIDs=[], theName=None):
"""
Make a thick solid from a face or a shell
Make a thick solid from a shape. If the input is a surface shape
(face or shell) the result is a thick solid. If an input shape is
a solid the result is a hollowed solid with removed faces.
Parameters:
theShape Face or Shell to be thicken
theShape Face or Shell to get thick solid or solid to get
hollowed solid.
theThickness Thickness of the resulting solid
theFacesIDs the list of face IDs to be removed from the
result. It is ignored if theShape is a face or a
shell. It is empty by default.
theName Object name; when specified, this parameter is used
for result publication in the study. Otherwise, if automatic
publication is switched on, default value is used for result name.
@ -4165,36 +4179,49 @@ class geomBuilder(object, GEOM._objref_GEOM_Gen):
New GEOM.GEOM_Object, containing the created solid
"""
# Example: see GEOM_TestAll.py
anObj = self.PrimOp.MakeThickening(theShape, theThickness, True)
RaiseIfFailed("MakeThickening", self.PrimOp)
self._autoPublish(anObj, theName, "pipe")
anObj = self.PrimOp.MakeThickening(theShape, theFacesIDs,
theThickness, True)
RaiseIfFailed("MakeThickSolid", self.PrimOp)
self._autoPublish(anObj, theName, "thickSolid")
return anObj
## Modifies a face or a shell to make it a thick solid
# @param theShape Face or Shell to be thicken
## Modifies a shape to make it a thick solid. If the input is a surface
# shape (face or shell) the result is a thick solid. If an input shape
# is a solid the result is a hollowed solid with removed faces.
# @param theShape Face or Shell to get thick solid or solid to get
# hollowed solid.
# @param theThickness Thickness of the resulting solid
# @param theFacesIDs the list of face IDs to be removed from the
# result. It is ignored if \a theShape is a face or a shell.
# It is empty by default.
#
# @return The modified shape
#
# @ref tui_creation_thickness "Example"
@ManageTransactions("PrimOp")
def Thicken(self, theShape, theThickness):
def Thicken(self, theShape, theThickness, theFacesIDs=[]):
"""
Modifies a face or a shell to make it a thick solid
Modifies a shape to make it a thick solid. If the input is a
surface shape (face or shell) the result is a thick solid. If
an input shape is a solid the result is a hollowed solid with
removed faces.
Parameters:
theBase Base shape to be extruded.
thePath Path shape to extrude the base shape along it.
theName Object name; when specified, this parameter is used
for result publication in the study. Otherwise, if automatic
publication is switched on, default value is used for result name.
theShape Face or Shell to get thick solid or solid to get
hollowed solid.
theThickness Thickness of the resulting solid
theFacesIDs the list of face IDs to be removed from the
result. It is ignored if \a theShape is a face or
a shell. It is empty by default.
Returns:
The modified shape
"""
# Example: see GEOM_TestAll.py
anObj = self.PrimOp.MakeThickening(theShape, theThickness, False)
RaiseIfFailed("MakeThickening", self.PrimOp)
anObj = self.PrimOp.MakeThickening(theShape, theFacesIDs,
theThickness, False)
RaiseIfFailed("Thicken", self.PrimOp)
return anObj
## Build a middle path of a pipe-like shape.

View File

@ -68,6 +68,7 @@ SET(GenerationGUI_HEADERS
GenerationGUI_FillingDlg.h
GenerationGUI_PipeDlg.h
GenerationGUI_PipePathDlg.h
GenerationGUI_ThiicknessDlg.h
)
# header files / to be processed by moc
@ -77,6 +78,7 @@ SET(_moc_HEADERS
GenerationGUI_FillingDlg.h
GenerationGUI_PipeDlg.h
GenerationGUI_PipePathDlg.h
GenerationGUI_ThicknessDlg.h
)
# --- sources ---
@ -91,6 +93,7 @@ SET(GenerationGUI_SOURCES
GenerationGUI_FillingDlg.cxx
GenerationGUI_PipeDlg.cxx
GenerationGUI_PipePathDlg.cxx
GenerationGUI_ThicknessDlg.cxx
${_moc_SOURCES}
)

View File

@ -37,6 +37,7 @@
#include "GenerationGUI_FillingDlg.h" // Method FILLING
#include "GenerationGUI_PipeDlg.h" // Method PIPE
#include "GenerationGUI_PipePathDlg.h" // Method RESTORE PATH
#include "GenerationGUI_ThicknessDlg.h" // Method THICKNESS
//=======================================================================
// function : GenerationGUI()
@ -74,7 +75,8 @@ bool GenerationGUI::OnGUIEvent( int theCommandID, SUIT_Desktop* parent )
case GEOMOp::OpRevolution: aDlg = new GenerationGUI_RevolDlg ( getGeometryGUI(), parent ); break;
case GEOMOp::OpFilling: aDlg = new GenerationGUI_FillingDlg ( getGeometryGUI(), parent ); break;
case GEOMOp::OpPipe: aDlg = new GenerationGUI_PipeDlg ( getGeometryGUI(), parent ); break;
case GEOMOp::OpPipePath: aDlg = new GenerationGUI_PipePathDlg( getGeometryGUI(), parent ); break;
case GEOMOp::OpPipePath: aDlg = new GenerationGUI_PipePathDlg ( getGeometryGUI(), parent ); break;
case GEOMOp::OpThickness: aDlg = new GenerationGUI_ThicknessDlg( getGeometryGUI(), parent ); break;
default: app->putInfo( tr( "GEOM_PRP_COMMAND" ).arg( theCommandID ) ); break;
}

View File

@ -722,7 +722,10 @@ bool GenerationGUI_PrismDlg::execute (ObjectList& objects)
aThickness = -aThickness;
}
anObj = anotherOper->MakeThickening(anObj, aThickness, /*copy=*/false);
GEOM::ListOfLong_var anArray = new GEOM::ListOfLong;
anObj = anotherOper->MakeThickening
(anObj, anArray, aThickness, /*copy=*/false);
}
if (!anObj->_is_nil())

View File

@ -0,0 +1,467 @@
// Copyright (C) 2007-2015 CEA/DEN, EDF R&D, OPEN CASCADE
//
// Copyright (C) 2003-2007 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
//
// This library is free software; you can redistribute it and/or
// modify it under the terms of the GNU Lesser General Public
// License as published by the Free Software Foundation; either
// version 2.1 of the License, or (at your option) any later version.
//
// This library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
// Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public
// License along with this library; if not, write to the Free Software
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
//
// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
//
// GEOM GEOMGUI : GUI for Geometry component
// File : GenerationGUI_ThicknessDlg.cxx
// Author : Sergey KHROMOV, Open CASCADE S.A.S.
#include "GenerationGUI_ThicknessDlg.h"
#include <GEOMBase.h>
#include <GeometryGUI.h>
#include <LightApp_SelectionMgr.h>
#include <SalomeApp_Application.h>
#include <SalomeApp_DoubleSpinBox.h>
#include <SUIT_Session.h>
#include <SUIT_ResourceMgr.h>
#include <QApplication>
#include <QCheckBox>
#include <QGridLayout>
#include <QGroupBox>
#include <QLabel>
#include <QLineEdit>
#include <QPushButton>
#include <QRadioButton>
#include <TopExp.hxx>
#include <TopTools_IndexedMapOfShape.hxx>
#include <Precision.hxx>
#define GEOM_SOLID_THICK 0
#define GEOM_SOLID_HOLLOWED 1
//==============================================================================
// class : GenerationGUI_ThicknessDlg()
// purpose :
//==============================================================================
GenerationGUI_ThicknessDlg::GenerationGUI_ThicknessDlg
(GeometryGUI* theGeometryGUI, QWidget* parent,
bool modal, Qt::WindowFlags fl)
: GEOMBase_Skeleton(theGeometryGUI, parent, modal, fl),
myFacesLbl (0),
myObjSelBtn (0),
myFacesSelBtn (0),
myObjEdit (0),
myFacesEdit (0),
myThicknessSpin (0),
myInsideCheck (0)
{
SUIT_ResourceMgr* aResMgr = SUIT_Session::session()->resourceMgr();
QPixmap image0(aResMgr->loadPixmap("GEOM", tr("ICON_SELECT")));
QPixmap image1(aResMgr->loadPixmap("GEOM", tr("ICON_DLG_THICKNESS")));
QPixmap image2
(aResMgr->loadPixmap("GEOM", tr("ICON_DLG_THICKNESS_HOLLOWED")));
setWindowTitle(tr("GEOM_THICKNESS_TITLE"));
/***************************************************************/
mainFrame()->GroupConstructors->setTitle(tr("GEOM_THICKNESS"));
mainFrame()->RadioButton1->setIcon(image1);
mainFrame()->RadioButton2->setIcon(image2);
mainFrame()->RadioButton3->setAttribute(Qt::WA_DeleteOnClose);
mainFrame()->RadioButton3->close();
mainFrame()->RadioButton1->setChecked(true);
QGroupBox *aMainGrp = new QGroupBox (tr("GEOM_ARGUMENTS"), this);
QGridLayout *aParamsLayout = new QGridLayout(aMainGrp);
QLabel *anObjLbl = new QLabel (tr("GEOM_OBJECT"), aMainGrp);
QLabel *aThicknessLbl = new QLabel (tr("GEOM_THICKNESS"), aMainGrp);
myFacesLbl = new QLabel (tr("GEOM_FACES"), aMainGrp);
myObjSelBtn = new QPushButton(aMainGrp);
myFacesSelBtn = new QPushButton(aMainGrp);
myObjEdit = new QLineEdit(aMainGrp);
myFacesEdit = new QLineEdit(aMainGrp);
myThicknessSpin = new SalomeApp_DoubleSpinBox(aMainGrp);
myInsideCheck = new QCheckBox(tr("GEOM_TOWARDS_INSIDE"), aMainGrp);
myObjSelBtn->setIcon(image0);
myFacesSelBtn->setIcon(image0);
myObjEdit->setReadOnly(true);
myObjEdit->setSizePolicy
(QSizePolicy(QSizePolicy::Expanding, QSizePolicy::Fixed));
myFacesEdit->setReadOnly(true);
myFacesEdit->setSizePolicy
(QSizePolicy(QSizePolicy::Expanding, QSizePolicy::Fixed));
aParamsLayout->setMargin(9);
aParamsLayout->setSpacing(6);
aParamsLayout->addWidget(anObjLbl, 0, 0);
aParamsLayout->addWidget(myObjSelBtn, 0, 1);
aParamsLayout->addWidget(myObjEdit, 0, 2);
aParamsLayout->addWidget(myFacesLbl, 1, 0);
aParamsLayout->addWidget(myFacesSelBtn, 1, 1);
aParamsLayout->addWidget(myFacesEdit, 1, 2);
aParamsLayout->addWidget(aThicknessLbl, 2, 0);
aParamsLayout->addWidget(myThicknessSpin, 2, 1, 1, 2);
aParamsLayout->addWidget(myInsideCheck, 3, 0, 1, 3);
QVBoxLayout* layout = new QVBoxLayout(centralWidget());
layout->setMargin(0);
layout->setSpacing(6);
layout->addWidget(aMainGrp);
myHelpFileName = "create_thickness_page.html";
/* Initialisation */
Init();
}
//==============================================================================
// function : ~GenerationGUI_ThicknessDlg()
// purpose :
//==============================================================================
GenerationGUI_ThicknessDlg::~GenerationGUI_ThicknessDlg()
{
// no need to delete child widgets, Qt does it all for us
}
//==============================================================================
// function : Init()
// purpose :
//==============================================================================
void GenerationGUI_ThicknessDlg::Init()
{
// Get setting of step value from file configuration
SUIT_ResourceMgr* resMgr = SUIT_Session::session()->resourceMgr();
double aStep = resMgr->doubleValue("Geometry", "SettingsGeomStep", 100);
double aThickness = 10.;
double aThicknessMin = Precision::Confusion() * 10.0;
initSpinBox(myThicknessSpin, aThicknessMin,
COORD_MAX, aStep, "length_precision");
myThicknessSpin->setValue(aThickness);
myObject.nullify();
myFaces.clear();
showOnlyPreviewControl();
// signals and slots connections
connect(buttonOk(), SIGNAL(clicked()), this, SLOT(ClickOnOk()));
connect(buttonApply(), SIGNAL(clicked()), this, SLOT(ClickOnApply()));
connect(this, SIGNAL(constructorsClicked(int)),
this, SLOT(ConstructorsClicked(int)));
connect(myObjSelBtn, SIGNAL(clicked()),
this, SLOT(SetEditCurrentArgument()));
connect(myFacesSelBtn, SIGNAL(clicked()),
this, SLOT(SetEditCurrentArgument()));
connect(myThicknessSpin, SIGNAL(valueChanged(double)),
this, SLOT(ValueChangedInSpinBox()));
connect(myGeomGUI, SIGNAL(SignalDefaultStepValueChanged(double)),
this, SLOT(SetDoubleSpinBoxStep(double)));
connect(myInsideCheck, SIGNAL(toggled(bool)),
this, SLOT(onChangeDirection(bool)));
connect(myGeomGUI->getApp()->selectionMgr(),
SIGNAL(currentSelectionChanged()),
this, SLOT(SelectionIntoArgument()));
initName(tr("GEOM_THICKNESS"));
ConstructorsClicked(0);
}
//==============================================================================
// function : SetDoubleSpinBoxStep()
// purpose : Double spin box management
//==============================================================================
void GenerationGUI_ThicknessDlg::SetDoubleSpinBoxStep (double step)
{
myThicknessSpin->setSingleStep(step);
}
//==============================================================================
// function : ConstructorsClicked()
// purpose : Radio button management
//==============================================================================
void GenerationGUI_ThicknessDlg::ConstructorsClicked (int constructorId)
{
switch (constructorId) {
case GEOM_SOLID_THICK:
myObjSelBtn->setDown(false);
myFacesLbl->hide();
myFacesSelBtn->hide();
myFacesEdit->hide();
myFaces.clear();
break;
case GEOM_SOLID_HOLLOWED:
myObjSelBtn->setDown(true);
myFacesLbl->show();
myFacesSelBtn->show();
myFacesEdit->show();
break;
default:
break;
}
myEditCurrentArgument = myObjEdit;
qApp->processEvents();
updateGeometry();
resize(minimumSizeHint());
SelectionIntoArgument();
}
//==============================================================================
// function : ClickOnOk()
// purpose :
//==============================================================================
void GenerationGUI_ThicknessDlg::ClickOnOk()
{
setIsApplyAndClose(true);
if (ClickOnApply()) {
ClickOnCancel();
}
}
//==============================================================================
// function : ClickOnApply()
// purpose :
//==============================================================================
bool GenerationGUI_ThicknessDlg::ClickOnApply()
{
if (!onAccept()) {
return false;
}
initName();
// activate selection and connect selection manager
ConstructorsClicked(getConstructorId());
return true;
}
//==============================================================================
// function : SelectionIntoArgument()
// purpose : Called when selection is changed or on dialog initialization or
// activation
//==============================================================================
void GenerationGUI_ThicknessDlg::SelectionIntoArgument()
{
erasePreview();
myEditCurrentArgument->setText("");
if (myEditCurrentArgument == myObjEdit) {
QList<TopAbs_ShapeEnum> aTypes;
const int anID = getConstructorId();
if (anID == GEOM_SOLID_THICK) {
aTypes << TopAbs_SHELL << TopAbs_FACE;
} else if (anID == GEOM_SOLID_HOLLOWED) {
aTypes << TopAbs_SOLID;
}
myObject = getSelected(aTypes);
if (myObject) {
QString aName = GEOMBase::GetName(myObject.get());
myEditCurrentArgument->setText(aName);
if (anID == GEOM_SOLID_HOLLOWED && myFaces.empty()) {
myFacesSelBtn->click();
}
}
} else if (myEditCurrentArgument == myFacesEdit) {
myFaces.clear();
myFaces = getSelected(TopAbs_FACE, -1);
int i = myFaces.count();
if (i == 1) {
myEditCurrentArgument->setText(GEOMBase::GetName(myFaces.first().get()));
} else if (i > 0) {
myEditCurrentArgument->setText
(QString::number( i ) + "_" + tr("GEOM_OBJECTS"));
}
}
processPreview();
}
//==============================================================================
// function : SetEditCurrentArgument()
// purpose :
//==============================================================================
void GenerationGUI_ThicknessDlg::SetEditCurrentArgument()
{
QPushButton* send = (QPushButton*)sender();
if (send == myObjSelBtn) {
myFacesSelBtn->setDown(false);
myEditCurrentArgument = myObjEdit;
globalSelection(GEOM_ALLSHAPES);
} else if (send == myFacesSelBtn) {
myObjSelBtn->setDown(false);
myEditCurrentArgument = myFacesEdit;
globalSelection(); // close local contexts, if any
localSelection(myObject.get(), TopAbs_FACE);
}
myEditCurrentArgument->setFocus();
const int anID = getConstructorId();
// after setFocus(), because it will be setDown(false) when loses focus
send->setDown(anID == GEOM_SOLID_HOLLOWED);
// seems we need it only to avoid preview disappearing, caused by selection
// mode change
processPreview();
}
//==============================================================================
// function : ActivateThisDialog()
// purpose :
//==============================================================================
void GenerationGUI_ThicknessDlg::ActivateThisDialog()
{
GEOMBase_Skeleton::ActivateThisDialog();
connect(myGeomGUI->getApp()->selectionMgr(),
SIGNAL(currentSelectionChanged()),
this, SLOT(SelectionIntoArgument()));
ConstructorsClicked(getConstructorId());
}
//==============================================================================
// function : enterEvent()
// purpose : when mouse enter onto the QWidget
//==============================================================================
void GenerationGUI_ThicknessDlg::enterEvent (QEvent*)
{
if (!mainFrame()->GroupConstructors->isEnabled())
ActivateThisDialog();
}
//==============================================================================
// function : ValueChangedInSpinBox()
// purpose :
//==============================================================================
void GenerationGUI_ThicknessDlg::ValueChangedInSpinBox()
{
processPreview();
}
//==============================================================================
// function : createOperation
// purpose :
//==============================================================================
GEOM::GEOM_IOperations_ptr GenerationGUI_ThicknessDlg::createOperation()
{
return getGeomEngine()->GetI3DPrimOperations(getStudyId());
}
//==============================================================================
// function : isValid
// purpose :
//==============================================================================
bool GenerationGUI_ThicknessDlg::isValid (QString& msg)
{
bool isOk = false;
switch (getConstructorId()) {
case GEOM_SOLID_THICK:
isOk = myThicknessSpin->isValid(msg, !IsPreview()) && myObject;
break;
case GEOM_SOLID_HOLLOWED:
isOk = myThicknessSpin->isValid(msg, !IsPreview()) &&
myObject && !myFaces.empty();
break;
default:
break;
}
return isOk;
}
//==============================================================================
// function : onChangeDirection(bool)
// purpose :
//==============================================================================
void GenerationGUI_ThicknessDlg::onChangeDirection(bool)
{
processPreview();
}
//==============================================================================
// function : execute
// purpose :
//==============================================================================
bool GenerationGUI_ThicknessDlg::execute (ObjectList& objects)
{
GEOM::GEOM_Object_var anObj;
GEOM::GEOM_I3DPrimOperations_var anOper =
GEOM::GEOM_I3DPrimOperations::_narrow(getOperation());
double aThickness = myThicknessSpin->value();
GEOM::ListOfLong_var anObjIDsList = new GEOM::ListOfLong();
TopoDS_Shape aShape;
if (GEOMBase::GetShape(myObject.get(), aShape)) {
TopTools_IndexedMapOfShape aMainMap;
QList<int> aListIDs;
TopExp::MapShapes(aShape, aMainMap);
for (int i = 0; i < myFaces.count(); i++) {
TopoDS_Shape aFace;
if (GEOMBase::GetShape(myFaces[i].get(), aFace)) {
int anIndex = aMainMap.FindIndex(aFace);
if (anIndex >= 0) {
aListIDs << anIndex;
}
}
}
if (!aListIDs.empty()) {
anObjIDsList->length(aListIDs.length());
for (int i = 0; i < aListIDs.length(); i++) {
anObjIDsList[i] = aListIDs[i];
}
}
}
if (myInsideCheck->isChecked()) {
aThickness = -aThickness;
}
anObj = anOper->MakeThickening
(myObject.get(), anObjIDsList.in(), aThickness, true);
if (!anObj->_is_nil()) {
objects.push_back(anObj._retn());
}
return true;
}

View File

@ -0,0 +1,83 @@
// Copyright (C) 2007-2015 CEA/DEN, EDF R&D, OPEN CASCADE
//
// Copyright (C) 2003-2007 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
//
// This library is free software; you can redistribute it and/or
// modify it under the terms of the GNU Lesser General Public
// License as published by the Free Software Foundation; either
// version 2.1 of the License, or (at your option) any later version.
//
// This library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
// Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public
// License along with this library; if not, write to the Free Software
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
//
// See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
//
// GEOM GEOMGUI : GUI for Geometry component
// File : GenerationGUI_ThicknessDlg.h
// Author : Sergey KHROMOV, Open CASCADE S.A.S.
#ifndef GENERATIONGUI_THICKNESSDLG_H
#define GENERATIONGUI_THICKNESSDLG_H
#include "GEOMBase_Skeleton.h"
//=================================================================================
// class : GenerationGUI_ThicknessDlg
// purpose :
//=================================================================================
class GenerationGUI_ThicknessDlg : public GEOMBase_Skeleton
{
Q_OBJECT
public:
GenerationGUI_ThicknessDlg(GeometryGUI*, QWidget* = 0,
bool = false, Qt::WindowFlags = 0);
~GenerationGUI_ThicknessDlg();
protected:
// redefined from GEOMBase_Helper
virtual GEOM::GEOM_IOperations_ptr createOperation();
virtual bool isValid( QString& );
virtual bool execute( ObjectList& );
private:
void Init();
void enterEvent( QEvent* );
private:
GEOM::GeomObjPtr myObject;
QList<GEOM::GeomObjPtr> myFaces;
QLabel *myFacesLbl;
QPushButton *myObjSelBtn;
QPushButton *myFacesSelBtn;
QLineEdit *myObjEdit;
QLineEdit *myFacesEdit;
SalomeApp_DoubleSpinBox *myThicknessSpin;
QCheckBox *myInsideCheck;
private slots:
void ClickOnOk();
bool ClickOnApply();
void ActivateThisDialog();
void SelectionIntoArgument();
void SetEditCurrentArgument();
void ConstructorsClicked(int);
void ValueChangedInSpinBox();
void SetDoubleSpinBoxStep(double);
void onChangeDirection(bool);
};
#endif // GENERATIONGUI_THICKNESSDLG_H