1
0
mirror of https://git.dev.opencascade.org/repos/occt.git synced 2025-08-14 13:30:48 +03:00

0026931: [Regression in 6.9.0] Exporting a face throws an exception

Writing periodic BSpline surfaces to IGES:
Replace segmentation of surface to setting new origin.
Fix face bounds if its length (in U or V) is more than period.

Segmentation of BSpline curve/surface:
Throw exception if segment length more than period.

Fix test case bugs moddata_1 bug14782:
bounds of segmentation must be the same as curve bounds, according to issue description.

Changes in classes Geom2d_BSplineCurve, Geom_BSplineCurve, Geom_BSplineSurface:
- Replace *Raise_if macros with unconditional exceptions where it does not affect on performance.
- Update comments in .hxx files in regard of raised exceptions.
This commit is contained in:
ika
2015-12-03 11:35:42 +03:00
committed by bugmaster
parent 83bb023e8d
commit 369a38aac2
10 changed files with 130 additions and 133 deletions

View File

@@ -242,8 +242,7 @@ Handle(IGESData_IGESEntity) GeomToIGES_GeomSurface::TransferSurface(const Handle
Standard_Real uShift = 0, vShift = 0;
mysurface->Bounds(U0,U1,V0,V1);
// cut segment from periodic surfaces for syncronization of pcurves ranges
// and surface bounds (issue 26138)
// fix bounds
if (!PeriodU) {
if (Umin < U0)
Umin = U0;
@@ -258,6 +257,8 @@ Handle(IGESData_IGESEntity) GeomToIGES_GeomSurface::TransferSurface(const Handle
uShift = ShapeAnalysis::AdjustToPeriod(Umin, U0, U1);
Umin += uShift;
Umax += uShift;
if (Umax - Umin > U1 - U0)
Umax = Umin + (U1 - U0);
}
if (!PeriodV) {
if (Vmin < V0)
@@ -273,44 +274,40 @@ Handle(IGESData_IGESEntity) GeomToIGES_GeomSurface::TransferSurface(const Handle
vShift = ShapeAnalysis::AdjustToPeriod(Vmin, V0, V1);
Vmin += vShift;
Vmax += vShift;
}
if (PeriodU || PeriodV) {
Standard_Boolean isNeedSegment = Standard_True;
isNeedSegment = Abs(Umax-Umin) > Precision::PConfusion() &&
Abs(Vmax-Vmin) > Precision::PConfusion();
Standard_Real uMaxShift = 0, vMaxShift = 0;
uMaxShift = ShapeAnalysis::AdjustToPeriod(Ufin, U0, U1);
vMaxShift = ShapeAnalysis::AdjustToPeriod(Vfin, V0, V1);
isNeedSegment &=
(PeriodU && Abs(uShift - uMaxShift) > Precision::PConfusion()) ||
(PeriodV && Abs(vShift - vMaxShift) > Precision::PConfusion());
if (isNeedSegment) {
try {
OCC_CATCH_SIGNALS
Handle(Geom_BSplineSurface) bspl = Handle(Geom_BSplineSurface)::DownCast ( start->Copy() );
if ( ! bspl.IsNull() ) {
bspl->CheckAndSegment(Umin, Umax, Vmin, Vmax);
if ((U1 - U0) - (Umax - Umin) > Precision::PConfusion())
PeriodU = Standard_False;
if ((V1 - V0) - (Vmax - Vmin) > Precision::PConfusion())
PeriodV = Standard_False;
mysurface = bspl;
}
}
catch ( Standard_Failure ) {
#ifdef OCCT_DEBUG
cout << "Warning: GeomToIGES_GeomSurface: can't trim bspline" << endl;
cout << "Warning: Exception in Segment(): " ;
Standard_Failure::Caught()->Print(cout);
#endif
}
}
if (Vmax - Vmin > V1 - V0)
Vmax = Vmin + (V1 - V0);
}
//unperiodize surface to get neccessary for IGES standard number of knots and mults
if ( mysurface->IsUPeriodic() ) {
// set new origin for periodic BSpline surfaces for synchronization of pcurves ranges
// and surface bounds (issue 26138)
if (mysurface->IsKind(STANDARD_TYPE(Geom_BSplineSurface))) {
Standard_Real uMaxShift = 0;
uMaxShift = ShapeAnalysis::AdjustToPeriod(Ufin, U0, U1);
if (Abs(uShift - uMaxShift) > Precision::PConfusion()) {
Handle(Geom_BSplineSurface) aBspl = Handle(Geom_BSplineSurface)::DownCast (mysurface->Copy());
Standard_Integer aLeft, aRight;
aBspl->LocateU(Umin, Precision::PConfusion(), aLeft, aRight);
aBspl->SetUOrigin(aLeft);
mysurface = aBspl;
}
}
mysurface->SetUNotPeriodic();
}
if ( mysurface->IsVPeriodic() ) {
// set new origin for periodic BSpline surfaces for synchronization of pcurves ranges
// and surface bounds (issue 26138)
if (mysurface->IsKind(STANDARD_TYPE(Geom_BSplineSurface))) {
Standard_Real vMaxShift = 0;
vMaxShift = ShapeAnalysis::AdjustToPeriod(Vfin, V0, V1);
if (Abs(vShift - vMaxShift) > Precision::PConfusion()) {
Handle(Geom_BSplineSurface) aBspl = Handle(Geom_BSplineSurface)::DownCast (mysurface->Copy());
Standard_Integer aLeft, aRight;
aBspl->LocateV(Vmin, Precision::PConfusion(), aLeft, aRight);
aBspl->SetVOrigin(aLeft);
mysurface = aBspl;
}
}
mysurface->SetVNotPeriodic();
}