DisplayConduit: Hide Objects from User Interaction (Osnaps, etc.)?

Hi everyone!!!

Small presentation for my first post: I’m Mario, an Italian architect working in France, Marseille!
I’m currently developing a custom plugin in C# using RhinoCommon to better handle object visibility following some personal rules.

I’m using a DisplayConduit to selectively hide some object types in specific viewports by setting CullObject = true in the ObjectCulling method. This successfully prevents the objects from being drawn in those viewports. I’ve already blocked selection using custom filters which works well. I know that the display conduit does not really hide the object from the scene, it just prevents drawing.

So now I’m facing an issue and i cannot find a workaround:

Even though objects are culled and cannot be selected, they still participate in object snaps and smart tracking. It is still possible to snap to points on these “hidden” objects.

I understand that object visibility controlled via Hide() or document visibility flags will resolve this, but I need to keep these objects visible in some viewports and hidden in others…so the standard visibility flags are not suitable in this case.

Is there a way to make an object completely ignored (not drawn, not selectable, not snappable) in a specific viewport via DisplayConduit or another technique? This filter should apply just to the active Viewport

Any help or insight would be greatly appreciated,

Mario

1 Like

Hi @mariodisibio,

one thing which came to my mind is to use RhinoObject.Attributes.ViewportId but it shows an object only in a single viewport once set. In other viewports it’s hidden, cannot be selected and snapped to and does not contribute to the scene bbox.

import Rhino
import scriptcontext
import rhinoscriptsyntax as rs
import System

def TogglePerViewObjVisibility():
    # makes object visible only in a certain view
    obj_id = rs.GetObject("Select object in desired view", 0, False, False)
    if not obj_id: return
    
    rh_obj = rs.coercerhinoobject(obj_id, True, True)
    view_id = scriptcontext.doc.Views.ActiveView.ActiveViewportID
    if rh_obj.Attributes.ViewportId == System.Guid.Empty:
        rh_obj.Attributes.ViewportId = view_id
    else:
        rh_obj.Attributes.ViewportId = System.Guid.Empty

    rh_obj.CommitChanges()
    
TogglePerViewObjVisibility()

My guess is you want the opposite and for multiple views ?

Another way would be to put the objects you’re trying to hide per viewport on specific layers and then control things using Layer.SetPerViewportVisible

_
c.

1 Like

Hi @clement,

thank you for your answer!

This is exactly the workaround I’ve found, and it works. On top of this I’m using an event watcher which detects the active viewport and dynamically override the ViewportId attribute to the objects concerned in order to correctly show/hide/lock in the correct context.

I guess this is working smoothly because I’m not manipulating too many objects… it seems quite a heavy operation for thousands of objects but for my purpose it is fine!

Thank you!!

Mario

Just for curiosity,
if i wanted to exclude totally an object from the scene using a display conduit I should have blocked the bbox generation? the bbox calculation is something that still i dont really understand… it is computed on a per-object basis or is global for the scene?

Mario

Hi @mariodisibio, imho that is a contradiction in itself since display conduits are made to display objects not to hide them :slight_smile:

In case of conduits, the bounding box is used to prevent clipping of objects shown in the conduit when they are drawn. The conduit bounding box can be created using eg:

    def CalculateBoundingBox(self, e):
        e.IncludeBoundingBox(self.YourBoundingBox)

You can also tell Rhino that this bounding box is considered when you use commands like _Zoom _Extents by writing below inside your conduit class:

   def CalculateBoundingBoxZoomExtents(self, e):
        e.IncludeBoundingBox(self.YourBoundingBox)

It is used globally for all viewports.

_
c.

1 Like