Changing active view is tempoerarily disabled?

python
dynamo

#1

Hi I am trying to change the active view via the python node in dynamo (1.2) . Currently I get the following error after initializing. It seems that the ui has a limitation, perhaps this is dynamo specific error?

************* Exception Text **************
Autodesk.Revit.Exceptions.InvalidOperationException: Setting active view is temporarily disabled.
   at Autodesk.Revit.DB.Document.CheckLimitations(APILimitations limitations, String action)
   at Autodesk.Revit.UI.UIDocument.set_ActiveView(View view)

My code (a snippet of it) looks something like below where view will be a view object. As you can see im using transaction manager to try to close open transactions, as mentioned somewhere, but to no avail.

# Import DocumentManager
clr.AddReference("RevitServices")
import RevitServices
from RevitServices.Persistence import DocumentManager
from RevitServices.Transactions import TransactionManager


doc = DocumentManager.Instance.CurrentDBDocument
uiapp = DocumentManager.Instance.CurrentUIApplication
uidoc = uiapp.ActiveUIDocument
app = uiapp.Application
view = uidoc.ActiveView 

def setActiveView(view):
        global doc
        TransactionManager.Instance.ForceCloseTransaction()
        uidoc.ActiveView = view
        TransactionManager.Instance.EnsureInTransaction(doc)
        TransactionManager.Instance.TransactionTaskDone()

#2

All the info you need about this is here


#3

So i saw that post, and in my code i tried ForceCloseTranscaction() it did not work. Are you saying it currently is not possible in the python node?


#4

that’s what I’m saying. :thumbsup:


#5

Well, this works better in revit python shell as a tool anyways. So quickly moved it to that, and now it works like a charm! thanks for the info.


#6

@chrisishere I’ve recently created a tool in Dynamo which needs to set a particular view. I thought I’d share this code snippet as there is another method you can use which does successfully set views. Its worth mentioning that you can’t set the uidoc.ActiveView in Revit’s Idling event. That’s a major drawback for Dynamo, since Dynamo operates inside this event (i.e. its not possible). Instead you need to use RequestViewChange(). Its executes asynchronously, so if you need to set a view first, then perform an action that’s dependent on this event inside the same node then you’ve got a problem. Also, a transaction has to be opened first and force closed using ForceCloseTransaction(), otherwise this method will still fail:

#Copyright 2016. All rights reserved. Bimorph Consultancy LTD, 5 St Johns Lane, London EC1M 4BH www.bimorph.co.uk
#Written by Thomas Mahon @Thomas__Mahon info@bimorph.co.uk Package: bimorphNodes
#GitHub: https://github.com/ThomasMahon/bimorphNodes/
#Follow: facebook.com/bimorphBIM | linkedin.com/company/bimorph-bim | @bimorphBIM

import clr

clr.AddReference("RevitServices")
import RevitServices
from RevitServices.Persistence import DocumentManager
from RevitServices.Transactions import TransactionManager

clr.AddReference("RevitAPI")
import Autodesk
from Autodesk.Revit.DB import *

doc = DocumentManager.Instance.CurrentDBDocument
uidoc = DocumentManager.Instance.CurrentUIDocument

TransactionManager.Instance.EnsureInTransaction(doc)
TransactionManager.Instance.ForceCloseTransaction()

view = UnwrapElement(IN[0])
uidoc.RequestViewChange( view )

#7

hmm I didnt know about RequestViewChange. Very cool, thanks for the update Thomas!


#8

@Thomas_Mahon
Would this node be available? Correct me if i am wrong, would this refresh an active view if included somewhere/part of a workflow? I was looking for a way to refresh the active view when the workflow reach a particular point.

Thanks a lot


#9

Do you mean refresh or set the view? If all you need to do is refresh the active view use UIDocument.RefreshActiveView.

RequestViewChange is used for external applications (i.e. Dynamo) to active a view. It’s asynchronous, which means it doesn’t execute in sequence; instead it waits for control to return to Revit and then the view is set. This therefore can only occur after Dynamo has completed its own process, and therein lies the problem; if you attempt to use this method as one of a number of steps in a Python script, whereby subsequent steps are dependent on the active view being set, the program will fail as control is still with Dynamo (i.e. the view wont be set yet).

An example of this limitation is deleting views. Say there are two views, A and B. B needs to be deleted. Its also the current active view. Active views cant be deleted, so A needs to be set as the active view first. We write a python script which calls the RequestViewChange to set A as the active view. In the next line of our code, we attempt to delete view B. As Dynamo has control as its busy executing the Python script, view A cant be made active, so the process will fail.


Cycle thru views on viewsets and make active view