Add a new method AIS_InteractiveContext::SetTransformPersistence, which sets transform persistence to object and selection.
Add a new method SelectMgr_SelectionManager::UpdateSelection, which re-adds selectable object in BVHs in all viewer selectors.
Add a new method SelectMgr_ViewerSelector::MoveSelectableObject, which moves object from set of not transform persistence objects to set of transform persistence objects (or vice versa).
Add a new method Graphic3d_TransformUtils::Convert, which converts gp_Trsf to Graphic3d_Mat4.
Remove the method PrsMgr_PresentableObject::SetTransformPersistence(flag, point).
Standard_EXPORT Standard_Boolean IsSModeIn (const Standard_Integer aMode) const;
+ //! Returns layer index.
+ Standard_Integer GetLayerIndex() const
+ {
+ return myLayerIndex;
+ }
theView->FitAll (aBndSelected, theMargin, theToUpdate);
}
+
+//=======================================================================
+//function : SetTransformPersistence
+//purpose :
+//=======================================================================
+void AIS_InteractiveContext::SetTransformPersistence (const Handle(AIS_InteractiveObject)& theObject,
+ const Graphic3d_TransModeFlags& theFlag,
+ const gp_Pnt& thePoint)
+{
+ theObject->SetTransformPersistence (theFlag, thePoint);
+
+ if (!myObjects.IsBound (theObject))
+ {
+ return;
+ }
+
+ mgrSelector->UpdateSelection (theObject);
+
+ const Standard_Integer aLayerId = myObjects.Find (theObject)->GetLayerIndex();
+ const Handle(V3d_Viewer)& aCurViewer = CurrentViewer();
+ for (aCurViewer->InitActiveViews(); aCurViewer->MoreActiveViews(); aCurViewer->NextActiveViews())
+ {
+ aCurViewer->ActiveView()->View()->InvalidateBVHData (aLayerId);
+ aCurViewer->ActiveView()->View()->InvalidateZLayerBoundingBox (aLayerId);
+ }
+}
//! for the view of the Interactive Object anObj.
Standard_EXPORT void Status (const Handle(AIS_InteractiveObject)& anObj, TCollection_ExtendedString& astatus) const;
+ //! Sets transform persistence.
+ Standard_EXPORT void SetTransformPersistence (const Handle(AIS_InteractiveObject)& theObj,
+ const Graphic3d_TransModeFlags& theFlag,
+ const gp_Pnt& thePoint = gp_Pnt (0.0, 0.0, 0.0));
//! Updates the current viewer, the viewer in Neutral Point.
//! Objects selected when there is no open local context
}
// Prevent zooming.
- if (Flags & Graphic3d_TMF_ZoomPers)
+ if ((Flags == Graphic3d_TMF_TriedronPers)
+ || (Flags & Graphic3d_TMF_ZoomPers))
{
- const T aDet00 = (2.0f / theViewportWidth) / theProjection.GetValue(0, 0);
- const T aDet11 = (2.0f / theViewportHeight) / theProjection.GetValue(1, 1);
- const T aDet2 = Max (aDet00, aDet11);
-
- theProjection.ChangeValue(0, 0) *= aDet00;
- theProjection.ChangeValue(1, 1) *= aDet11;
- theProjection.ChangeValue(2, 2) *= aDet2;
- }
-
- if (Flags == Graphic3d_TMF_TriedronPers)
- {
- // Compute fixed-zoom multiplier. Actually function works ugly with TelPerspective!
- const T aDet2 = static_cast<T> (0.002) / Max (theProjection.GetValue (1, 1), theProjection.GetValue (0, 0));
-
- theProjection.ChangeValue (0, 0) *= aDet2;
- theProjection.ChangeValue (1, 1) *= aDet2;
- theProjection.ChangeValue (2, 2) *= aDet2;
+ const T aSize = static_cast<T> (1.0);
+ const Standard_Integer aViewport[4] = { 0, 0, theViewportHeight, theViewportHeight };
+ NCollection_Mat4<T> aWorldView;
+ aWorldView.InitIdentity();
+
+ NCollection_Vec3<T> aWinCoordsRefPoint;
+ Graphic3d_TransformUtils::Project (static_cast<T> (Point.x()),
+ static_cast<T> (Point.y()),
+ static_cast<T> (Point.z()),
+ theWorldView, theProjection, aViewport,
+ aWinCoordsRefPoint.x(), aWinCoordsRefPoint.y(), aWinCoordsRefPoint.z());
+
+ NCollection_Vec3<T> anUnProj1;
+ Graphic3d_TransformUtils::UnProject (aWinCoordsRefPoint.x(), aWinCoordsRefPoint.y(), aWinCoordsRefPoint.z(),
+ aWorldView, theProjection, aViewport,
+ anUnProj1.x(), anUnProj1.y(), anUnProj1.z());
+
+ NCollection_Vec3<T> anUnProj2;
+ Graphic3d_TransformUtils::UnProject (aWinCoordsRefPoint.x(), aWinCoordsRefPoint.y() + aSize, aWinCoordsRefPoint.z(),
+ aWorldView, theProjection, aViewport,
+ anUnProj2.x(), anUnProj2.y(), anUnProj2.z());
+
+ const T aScale = (anUnProj2.y() - anUnProj1.y()) / aSize;
+
+ Graphic3d_TransformUtils::Scale (theWorldView, aScale, aScale, aScale);
}
// Prevent translation by nullifying translation component.
theProjection.SetValue (2, 3, static_cast<T> (0.0));
}
- // Prevent scaling-on-axis.
- if (Flags & Graphic3d_TMF_ZoomPers)
- {
- NCollection_Vec3<T> aVecX = theWorldView.GetColumn (0).xyz();
- NCollection_Vec3<T> aVecY = theWorldView.GetColumn (1).xyz();
- NCollection_Vec3<T> aVecZ = theWorldView.GetColumn (2).xyz();
- T aScaleX = aVecX.Modulus();
- T aScaleY = aVecY.Modulus();
- T aScaleZ = aVecZ.Modulus();
- for (Standard_Integer anI = 0; anI < 3; ++anI)
- {
- theWorldView.ChangeValue (0, anI) /= aScaleX;
- theWorldView.ChangeValue (1, anI) /= aScaleY;
- theWorldView.ChangeValue (2, anI) /= aScaleZ;
- }
- }
-
// Prevent rotation by nullifying rotation component.
if (Flags & Graphic3d_TMF_RotatePers)
{
typedef Graphic3d_Vec4 Vec4;
};
+ //! Converts gp_Trsf to Graphic3d_Mat4.
+ template<class T>
+ static void Convert (const gp_Trsf& theTransformation,
+ typename MatrixType<T>::Mat4& theOut);
+
//! Constructs a 3D orthographic projection matrix.
template<class T>
static void Ortho (typename MatrixType<T>::Mat4& theOut,
T theX,
T theY,
T theZ);
+
+ //! Returns scaling factor from 3x3 affine matrix.
+ template<class T>
+ static Standard_Real ScaleFactor (const typename MatrixType<T>::Mat4& theMatrix);
+}
+
+// =======================================================================
+// function : Convert
+// purpose :
+// =======================================================================
+template<class T>
+void Graphic3d_TransformUtils::Convert (const gp_Trsf& theTransformation,
+ typename MatrixType<T>::Mat4& theOut)
+{
+ theOut.InitIdentity();
+
+ // Copy a 3x3 submatrix.
+ theOut.ChangeValue (0, 0) = theTransformation.Value (1, 1);
+ theOut.ChangeValue (0, 1) = theTransformation.Value (1, 2);
+ theOut.ChangeValue (0, 2) = theTransformation.Value (1, 3);
+ theOut.ChangeValue (1, 0) = theTransformation.Value (2, 1);
+ theOut.ChangeValue (1, 1) = theTransformation.Value (2, 2);
+ theOut.ChangeValue (1, 2) = theTransformation.Value (2, 3);
+ theOut.ChangeValue (2, 0) = theTransformation.Value (3, 1);
+ theOut.ChangeValue (2, 1) = theTransformation.Value (3, 2);
+ theOut.ChangeValue (2, 2) = theTransformation.Value (3, 3);
+
+ // Add a translate component.
+ theOut.ChangeValue (0, 3) = theTransformation.TranslationPart().X();
+ theOut.ChangeValue (1, 3) = theTransformation.TranslationPart().Y();
+ theOut.ChangeValue (2, 3) = theTransformation.TranslationPart().Z();
}
// =======================================================================
return Standard_True;
}
+// =======================================================================
+// function : ScaleFactor
+// purpose :
+// =======================================================================
+template<class T>
+static Standard_Real Graphic3d_TransformUtils::ScaleFactor (const typename MatrixType<T>::Mat4& theMatrix)
+{
+ // The determinant of the matrix should give the scale factor (cubed).
+ const T aDeterminant = (theMatrix.GetValue (0, 0) * theMatrix.GetValue (1, 1) * theMatrix.GetValue (2, 2) +
+ theMatrix.GetValue (0, 1) * theMatrix.GetValue (1, 2) * theMatrix.GetValue (2, 0) +
+ theMatrix.GetValue (0, 2) * theMatrix.GetValue (1, 0) * theMatrix.GetValue (2, 1))
+ - (theMatrix.GetValue (0, 2) * theMatrix.GetValue (1, 1) * theMatrix.GetValue (2, 0) +
+ theMatrix.GetValue (0, 0) * theMatrix.GetValue (1, 2) * theMatrix.GetValue (2, 1) +
+ theMatrix.GetValue (0, 1) * theMatrix.GetValue (1, 0) * theMatrix.GetValue (2, 2));
+
+ return Pow (static_cast<Standard_Real> (aDeterminant), 1.0 / 3.0);
+}
+
#endif // _Graphic3d_TransformUtils_HeaderFile
{
if (!theToIgnoreInfiniteFlag && (aStructure->TransformPersistence.Flags & Graphic3d_TMF_ZoomPers))
{
- if (!theCamera->IsOrthographic())
- {
- continue;
- }
-
BVH_Vec4f aTPPoint (static_cast<float> (aStructure->TransformPersistence.Point.x()),
static_cast<float> (aStructure->TransformPersistence.Point.y()),
static_cast<float> (aStructure->TransformPersistence.Point.z()),
aCtx->ModelWorldState.Push();
aCtx->ModelWorldState.SetCurrent (Transformation);
+ const Standard_Boolean anOldGlNormalize = aCtx->IsGlNormalizeEnabled();
+
+#if !defined(GL_ES_VERSION_2_0)
+ // detect scale transform
+ if (aCtx->core11 != NULL)
+ {
+ const Standard_ShortReal aScaleX = Transformation.GetRow (0).xyz().SquareModulus();
+ if (Abs (aScaleX - 1.f) > Precision::Confusion())
+ {
+ aCtx->SetGlNormalizeEnabled (Standard_True);
+ }
+ }
+#endif
+
if (TransformPersistence.Flags)
{
OpenGl_Mat4 aProjection = aCtx->ProjectionState.Current();
aCtx->ProjectionState.SetCurrent (aProjection);
aCtx->WorldViewState.SetCurrent (aWorldView);
aCtx->ApplyProjectionMatrix();
- }
- // detect scale transform
- const Standard_Boolean anOldGlNormalize = aCtx->IsGlNormalizeEnabled();
- const Standard_ShortReal aScaleX = aCtx->ModelWorldState.Current().GetRow (0).xyz().SquareModulus();
- if (Abs (aScaleX - 1.f) > Precision::Confusion())
- {
- aCtx->SetGlNormalizeEnabled (Standard_True);
+ #if !defined(GL_ES_VERSION_2_0)
+ if (!aCtx->IsGlNormalizeEnabled()
+ && aCtx->core11 != NULL)
+ {
+ const Standard_Real aScale = Graphic3d_TransformUtils::ScaleFactor<Standard_ShortReal> (aWorldView);
+ if (Abs (aScale - 1.0f) > Precision::Confusion())
+ {
+ aCtx->SetGlNormalizeEnabled (Standard_True);
+ }
+ }
+ #endif
}
// Take into account transform persistence
const Standard_Integer theWindowHeight,
const Standard_Boolean theToIgnoreInfiniteFlag) const
{
- if (myZLayers.LayerIDs().IsBound (theLayerId) && theCamera->IsOrthographic())
+ if (myZLayers.LayerIDs().IsBound (theLayerId))
{
return myZLayers.Layer (theLayerId).considerZoomPersistenceObjects (Identification(),
theCamera,
}
}
-//=======================================================================
-//function : SetTransformPersistence
-//purpose :
-//=======================================================================
-void PrsMgr_PresentableObject::SetTransformPersistence(
- const Graphic3d_TransModeFlags& TheFlag )
-{
- SetTransformPersistence( TheFlag, gp_Pnt(0,0,0) );
-}
-
//=======================================================================
//function : GetTransformPersistence
//purpose :
//! - X < 0.0, Y > 0.0 - left upper corner of view window;
//! - X < 0.0, Y < 0.0 - left lower corner of view window.
//! And Z coordinate defines the gap from border of view window (except center position).
- Standard_EXPORT virtual void SetTransformPersistence (const Graphic3d_TransModeFlags& aFlag, const gp_Pnt& APoint);
-
- //! Calls previous method with point (0,0,0)
- Standard_EXPORT void SetTransformPersistence (const Graphic3d_TransModeFlags& aFlag);
-
+ Standard_EXPORT virtual void SetTransformPersistence (const Graphic3d_TransModeFlags& aFlag, const gp_Pnt& APoint = gp_Pnt (0.0, 0.0, 0.0));
+
//! Gets Transform Persistence Mode for this object
Standard_EXPORT Graphic3d_TransModeFlags GetTransformPersistenceMode() const;
}
if (aCS->GetTransformPersistenceMode() != Graphic3d_TMF_2d)
{
- aCS->SetTransformPersistence (Graphic3d_TMF_2d, gp_Pnt (-1,-1,0));
+ aContext->SetTransformPersistence (aCS, Graphic3d_TMF_2d, gp_Pnt (-1,-1,0));
}
Standard_Integer aWinWidth, aWinHeight;
V->Window()->Size (aWinWidth, aWinHeight);
}
}
}
+
+//=======================================================================
+//function : UpdateSelection
+//purpose :
+//=======================================================================
+void SelectMgr_SelectionManager::UpdateSelection (const Handle(SelectMgr_SelectableObject)& theObject)
+{
+ if (myGlobal.Contains (theObject))
+ {
+ for (TColStd_MapIteratorOfMapOfTransient aSelectorsIter (mySelectors); aSelectorsIter.More(); aSelectorsIter.Next())
+ {
+ Handle(SelectMgr_ViewerSelector) aSelector = Handle(SelectMgr_ViewerSelector)::DownCast (aSelectorsIter.Key());
+ if (aSelector->Contains (theObject))
+ {
+ aSelector->MoveSelectableObject (theObject);
+ }
+ }
+ }
+
+ if (myLocal.IsBound (theObject))
+ {
+ const SelectMgr_SequenceOfSelector& aSelectors = myLocal (theObject);
+ for (SelectMgr_SequenceOfSelector::Iterator aSelectorsIter (aSelectors); aSelectorsIter.More(); aSelectorsIter.Next())
+ {
+ Handle(SelectMgr_ViewerSelector)& aSelector = aSelectorsIter.ChangeValue();
+ if (aSelector->Contains (theObject))
+ {
+ aSelector->MoveSelectableObject (theObject);
+ }
+ }
+ }
+}
const Standard_Integer theMode,
const Standard_Integer theNewSens);
+ //! Re-adds selectable object in BVHs in all viewer selectors.
+ Standard_EXPORT void UpdateSelection (const Handle(SelectMgr_SelectableObject)& theObj);
+
DEFINE_STANDARD_RTTIEXT(SelectMgr_SelectionManager,MMgt_TShared)
protected:
{
const Graphic3d_Mat4d& aProjection = mySelectingVolumeMgr.ProjectionMatrix();
const Graphic3d_Mat4d& aWorldView = mySelectingVolumeMgr.WorldViewMatrix();
+
Standard_Integer aViewportWidth;
Standard_Integer aViewportHeight;
mySelectingVolumeMgr.WindowSize (aViewportWidth, aViewportHeight);
}
}
+//=======================================================================
+// function : MoveSelectableObject
+// purpose :
+//=======================================================================
+void SelectMgr_ViewerSelector::MoveSelectableObject (const Handle(SelectMgr_SelectableObject)& theObject)
+{
+ if (!mySelectableObjects.Remove (theObject))
+ {
+ mySelectableObjectsTrsfPers.Remove (theObject);
+ }
+
+ if (!theObject->TransformPersistence().Flags)
+ {
+ mySelectableObjects.Append (theObject);
+ }
+ else
+ {
+ mySelectableObjectsTrsfPers.Append (theObject);
+ }
+}
+
//=======================================================================
// function : RemoveSelectableObject
// purpose : Removes selectable object from map of selectable ones
Standard_EXPORT void AddSelectionToObject (const Handle(SelectMgr_SelectableObject)& theObject,
const Handle(SelectMgr_Selection)& theSelection);
+ //! Moves existing object from set of not transform persistence objects
+ //! to set of transform persistence objects (or vice versa).
+ Standard_EXPORT void MoveSelectableObject (const Handle(SelectMgr_SelectableObject)& theObject);
+
//! Removes selectable object from map of selectable ones
Standard_EXPORT void RemoveSelectableObject (const Handle(SelectMgr_SelectableObject)& theObject);
}
if (toSetTrsfPers)
{
- aShape->SetTransformPersistence (aTrsfPersFlags, aTPPosition);
+ aCtx->SetTransformPersistence (aShape, aTrsfPersFlags, aTPPosition);
}
if (anObjDispMode != -2)
{
}
if (toSetTrsfPers)
{
- aShape->SetTransformPersistence (aTrsfPersFlags, aTPPosition);
+ aCtx->SetTransformPersistence (aShape, aTrsfPersFlags, aTPPosition);
}
if (anObjDispMode != -2)
{
{
const Graphic3d_Mat4d& aProjection = aMgr.ProjectionMatrix();
const Graphic3d_Mat4d& aWorldView = aMgr.WorldViewMatrix();
+
Standard_Integer aViewportWidth = 0;
Standard_Integer aViewportHeight = 0;
aMgr.WindowSize (aViewportWidth, aViewportHeight);
if (aTrsfPersFlags != Graphic3d_TMF_None)
{
- aTextPrs->SetTransformPersistence (aTrsfPersFlags, aTPPosition);
+ aContext->SetTransformPersistence (aTextPrs, aTrsfPersFlags, aTPPosition);
aTextPrs->SetZLayer(Graphic3d_ZLayerId_TopOSD);
if (aTextPrs->Position().Z() != 0)
{
}
else if (aTrsfPersFlags != aTextPrs->TransformPersistence().Flags)
{
- aTextPrs->SetTransformPersistence (aTrsfPersFlags);
+ aContext->SetTransformPersistence (aTextPrs, aTrsfPersFlags);
}
ViewerTest::Display (aName, aTextPrs, Standard_False);
return 0;
}
if (aCS->GetTransformPersistenceMode() != Graphic3d_TMF_2d)
{
- aCS->SetTransformPersistence (Graphic3d_TMF_2d, gp_Pnt (-1,-1,0));
+ aContext->SetTransformPersistence (aCS, Graphic3d_TMF_2d, gp_Pnt (-1.0, -1.0, 0.0));
}
Standard_Real aMinRange = aCS->GetMin();
aLineType, aWidth,
aTransparency);
- aLine->SetTransformPersistence (Graphic3d_TMF_2d,gp_Pnt(-1,-1,0));
+ aContext->SetTransformPersistence (aLine, Graphic3d_TMF_2d, gp_Pnt (-1.0, -1.0, 0.0));
aLine->SetZLayer (Graphic3d_ZLayerId_TopOSD);
aLine->SetToUpdate();
aContext->Display (aLine, Standard_True);
vdisplay b2 -trsfPers zoom -trsfPersPos 200 200 200
vsetlocation b2 -25 -25 -25
-vmoveto 384 78
-if { ![checkcolor 384 78 0 1 1] } {
+vmoveto 387 77
+if { ![checkcolor 387 77 0 1 1] } {
puts "Error picking zoom persistence object"
}
-vmoveto 356 96
-if { ![checkcolor 356 96 0 1 1] } {
+vmoveto 352 96
+if { ![checkcolor 352 96 0 1 1] } {
puts "Error picking zoom persistent object with location"
}
vselect 330 120 400 50
-if { ![checkcolor 384 78 0.8 0.8 0.8] || ![checkcolor 356 96 0.8 0.8 0.8] } {
+if { ![checkcolor 387 77 0.8 0.8 0.8] || ![checkcolor 352 96 0.8 0.8 0.8] } {
puts "Error selecting zoom persistence object(s)"
}
-
# 2) Rotate persistence
vdisplay b3 -trsfPers rotate -trsfPersPos -200 -200 -200
# 4) Trihedron persistence
vdisplay b5 -trsfPers trihedron -trsfPersPos -1 -1 300
-vmoveto 90 300
-if { ![checkcolor 90 300 0 1 1] } {
+vmoveto 132 300
+if { ![checkcolor 132 300 0 1 1] } {
puts "Error picking trihedron persistence object"
}
-vselect 50 380 140 280
-if { ![checkcolor 90 300 0.8 0.8 0.8] } {
+vselect 50 223 235 395
+if { ![checkcolor 132 300 0.8 0.8 0.8] } {
puts "Error selecting trihedron persistence object"
}
--- /dev/null
+puts "============"
+puts "CR26641"
+puts "============"
+puts ""
+
+##############################################################################################################
+# 0026641: Visualization, TKOpenGl - handle correctly transformation persistence within perspective projection
+##############################################################################################################
+
+vinit
+vclear
+
+box b0 30 0 0 10 10 10
+box b1 -30 -30 30 10 30 20
+vdisplay b0
+vdisplay b1
+vfit
+
+vdump ${imagedir}/${casename}_none_pers_ortho.png
+
+vdisplay b1 -trsfPers zoom -trsfPersPos -30 -30 30
+vfit
+
+vdump ${imagedir}/${casename}_zoom_pers_ortho.png
+
+vcamera -persp
+vfit
+
+vdump ${imagedir}/${casename}_zoom_pers_persp.png
+
+vselect 30 70
+
+if {[vnbselected] != 1} {
+ puts "ERROR: Transform persistence object is not selected!"
+}