Community
Fusion API and Scripts
Got a new add-in to share? Need something specialized to be scripted? Ask questions or share what you’ve discovered with the community.
cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

Script too fast for UI to keep up

5 REPLIES 5
SOLVED
Reply
Message 1 of 6
Anonymous
646 Views, 5 Replies

Script too fast for UI to keep up

Programatically, I am selecting multiple pairs of faces to then align

 

The function shown below is called many times in rapid succession and appeared to show inconsistent / wrong results

 

On my old slow laptop, it always worked correctly

 

In debug mode it always worked correctly

 

On my desktop machine it never worked

 

I concluded that the UI is lagging behind the script so put a blocking pause in place and that fixes it 

 

Is there a better way to detremine if the UI has finished so it's safe to move on and get the next pair?

 

The code is commented to show the latest and best result so far but it's not a good solution

 

function alignFaces01(face1,face2) {
  // This function is called many times in rapid succession after programatically determining a 
  // long series of faces to align.
  // 
  // Without the time wasting loop, it appears to have non deterministic behaviour 
  // and random faces will be aligned with each other
  //
  // It was confusing as in debug mode, it always worked correctly
  // and on my laptop (a much slower machine it also worked correctly)
  //
  // I concluded that the UI was not responding quick enough so put in the ui refresh 
  // That didn't work
  // 
  // The sleep function does force it to work but I can't consider that a good solution
  // Is there any good practise that will work reliably?
  
  var app = adsk.core.Application.get();
  var ui  = app.userInterface;

  // Add these faces to the active selection.
  var theseSelections = ui.activeSelections;
  
  // clear any selections pre existing
  theseSelections.clear;
  
  // add the 1st face to the selection  
  theseSelections.add(face1);
  
  // add the 2nd face to the selection
  theseSelections.add(face2);

  // Get the Align Component command and execute it.
  var alignCommand = ui.commandDefinitions.itemById('AlignComponentsCmd');
  alignCommand.execute();
  
  // make sure the viewport has caught up with all the edits
  // this does not work
  app.activeViewport.refresh(); 

  // create delay by pointlessly looping round
  // This works but is terrible practise!!
  // 100 milliseconds does the trick on my desktop machine
  // 50 milliseconds sometimes does it
  // 25 milliseconds does not do it
  sleepOMG(100);

}
5 REPLIES 5
Message 2 of 6
Anonymous
in reply to: Anonymous

Well a few hours away brought me a better solution. 

 

Still doesn't feel excellent but it's better than a fixed loop.

 

  // wait here until they are co planar
  var facesAreCoPlanar = false;
  while (facesAreCoPlanar == false) {
    var plane1 = face1.geometry;
    var plane2 = face2.geometry;
    facesAreCoPlanar = plane1.isCoPlanarTo(plane2);    
  }
Message 3 of 6
liujac
in reply to: Anonymous

Hi,

 

CommandDefinition.execute method defaults to execute command on application idle if there is no input passed to the method, that means the commands is not executed immediately. You can try to set 'executeImmediately' to true as below to execute the command immediately.

 

 

var alignCommand = ui.commandDefinitions.itemById('AlignComponentsCmd');
var nvs = adsk.core.NamedValues.create();
nvs.add('executeImmediately', adsk.core.ValueInput.createByString('true'));
alignCommand.execute(nvs);

 

Regards,

Jack

 

Message 4 of 6
Anonymous
in reply to: liujac

Thanks Jack

Seems to work but I'm on my slow laptop so difficult to recreate the problem until I'm back in the UK.

Does it block further execution until it's finished or just start it immediately and then continue anyway?

Cheers

Peter
Message 5 of 6
liujac
in reply to: Anonymous

For your case above, you selected two faces that satisfied the inputs to execute the AlignComponentsCommand, so it could block further execution until it's finished if set 'executeImmediately' to true. Executing internal command is not the formal solution. There are other formal solutions to align components:

1. Use Occurrence.transform, in this way you have to calculate the matrix first.

2. Use Joint APIs. This way would be more flexible.

 

Regards,

Jack

Message 6 of 6
Anonymous
in reply to: liujac

Thanks.

I'm finding the matrix a bit hard to understand 😞

Is there any good tutorials or code examples that could help me understand it?

Can't find what you're looking for? Ask the community or share your knowledge.

Post to forums  

Autodesk DevCon in Munich May 28-29th


Autodesk Design & Make Report