Loft factory question
All  1-11  12-20

Previous
Next
 From:  Martin (MARTIN3D)
5493.12 
Good morning. Lots of activity while I was asleep. Thank you.

Thanks Brian, for your help. I do examine the command files and even looked into EditOrientations.js but like you didn't understand. Fortunately in my case the script can stay simple without the need for a list. I like simple and compared to your scripts mine are humble :-)

Thanks Michael, of course it must be .commit()! I used it a hundred times before but that comes from typing from memory.


What I don't understand is the difference between factory.update() and factory.calculate().

Is the following correct?
factory.commit() calculates the result and puts it into the scene (geometryDatabase).
factory.update() just calculates the result and (with the exception of asynchronous factories like sweep or boolean) it can be assigned to a variable using factory.getCreatedObjects();
factory.calculate() also just calculates the result and it can be directly assigned to a variable.

Why can't I just write var x = factory.commit();?
Why is there an .update() and a .calculate() method when it looks like they do the same?

I hope it's not too complicated to explain.
  Reply Reply More Options
Post Options
Reply as PM Reply as PM
Print Print
Mark as unread Mark as unread
Relationship Relationship
IP Logged

Previous
Next
 From:  bemfarmer
5493.13 In reply to 5493.12 
Here is an old post with some info:
http://50.56.177.237/forum/index.php?webtag=MOI&msg=3541.1
I only vaguely grasp it, more or less. :-)
  Reply Reply More Options
Post Options
Reply as PM Reply as PM
Print Print
Mark as unread Mark as unread
Relationship Relationship
IP Logged

Previous
Next
 From:  Martin (MARTIN3D)
5493.14 In reply to 5493.13 
Thanks Brian, thats an interesting read that should answer my question. But I fear I also have to read it many, many more times to get the most out of it. Very funny is the comment by Burrman in post 7 :-)
  Reply Reply More Options
Post Options
Reply as PM Reply as PM
Print Print
Mark as unread Mark as unread
Relationship Relationship
IP Logged

Previous
Next
 From:  Michael Gibson
5493.15 In reply to 5493.12 
Hi Martin,

quote:

Is the following correct?
factory.commit() calculates the result and puts it into the scene (geometryDatabase).
factory.update() just calculates the result and (with the exception of asynchronous factories like sweep or boolean) it can be assigned to a variable using factory.getCreatedObjects();
factory.calculate() also just calculates the result and it can be directly assigned to a variable.

Why can't I just write var x = factory.commit();?
Why is there an .update() and a .calculate() method when it looks like they do the same?


So it will probably make more sense if you consider that the entire factory mechanism is primarily designed to be used in an interactive command and not so much for use with custom scripting like you're doing.

The way a factory works is that you fill in the inputs, then when the inputs change you can either call .update() directly on the factory or there are also various binding mechanisms that binds a changing value to the input (like a point picker can bind its result to a factory input to push the current point the pointpicker is tracking onto the input) and those binding based methods usually automatically call factory.update() as part of its mechanisms so you don't have to call it manually in those cases.


> factory.update() just calculates the result and (with the exception of asynchronous factories like sweep or boolean)
> it can be assigned to a variable using

This part is not quite right - update calculates the result and also puts the generated output into the geometry database and deletes input objects if it's the type of command that removes inputs as well. It does all that work because it's meant to show the current result of the factory's calculation in response to a changed UI control or changed pointpicker location or things like that, and in order to display any geometry involves not just doing an isolated calculation but also putting the new objects into the geometry database. It's all the contents of the geometry database that are displayed inside of viewports, so if you want something to show up on the screen it has to not just be internally calculated but also has to go onto the geometry database.

The way regular commands are set up you can usually interactively adjust many parameters and point locations and stuff like that and see the result on the screen update, so normally there are many calls to factory.update() through this interactive part of a command.

Then usually a command can either be finished by pushing Done or it can be canceled. The way the factory mechanism works is that if you push cancel any active factory that has been created during the command will have any of its changes reverted - any generated objects will be removed from the geometry database and the original objects restored to be visible again if it was a command that removed existing objects. In order to not have that canceling mechanism be triggered you must call factory.commit() - that tells the command factory mechanism that it should consider that factory to be successfully and fully completed by the user pushing "Done" and finishing the command instead of being canceled in any way (there are various ways that things can get canceled, like with a new command being started, or the program exiting, not only just from "Cancel" being pushed).

When .commit() is called it also checks to see if there has been any previous .update() ever called and if there has not it will automatically call update() itself. It's only actually in .update() that things are actually calculated.


So anyway this whole update/cancel/commit mechanism is set up to be used in this way mostly with a command using one single factory for the command.

You're using it in a pretty different way from that, wanting to chain the results of several different factories together instead of just using one factory that was tailor-made for the command.

I've tried to add in a .calculate() method in order to help with the kind of use that you're doing - when you call .calculate() on a factory, it only creates the output objects and does not try to remove or put anything in the geometry database at all, unlike update(). So while .update() is primarily a method that gives visual results (it basically updates the screen to reflect the new factory input values), .calculate() does not do anything visual at all and only generates geometry that could then be used for other purposes in the script like intermediate calculations.

At one point I had been hoping to just have one single script mechanism for geometry creation and to be able to use the factory method for both interactive commands (with .update()/.commit()/.cancel() ) as well as using the same infrastructure for custom scripting like you're trying to do. But I think that it's not a great fit for both methods, I think that instead I'm going to implement some more direct functions in the script API to generate objects, stuff like moi.geometryDatabase.createLine( from, to ), and things like that rather than only have everything go through the factory mechanism only. But like a lot of feature areas I simply have not had enough time available yet to focus on making that new API layer. APIs are not great areas to slap together quickly because once people start using them it becomes quite difficult to make any changes in them which break existing scripts. Things that require extra care to do right tend to be time consuming and with time in short supply it can be difficult to implement time consuming areas of work...

- Michael
  Reply Reply More Options
Post Options
Reply as PM Reply as PM
Print Print
Mark as unread Mark as unread
Relationship Relationship
IP Logged

Previous
Next
 From:  Martin (MARTIN3D)
5493.16 In reply to 5493.15 
Hi Michael,

I'm actually quite happy with the way scripting MoI works right now. When I use it in the same way as I would do things manually i.e. just use .commit() and a .selectAll() / .invertSelection() / deselectAll() combo to put things into the next factory I already can do anything I want. It just requires careful planning and keeping track of whats selected and whats not.

If in the next beta the .update() / getCreatedObjects() / .cancel() combo works for sweeps and booleans using variables will make scripting even easier because I can use object.selected = true; or objectlist.setProperty('selected', true);


And if its just for easier coding I can already have that with an external Javascript file.
Your line example could already be as simple as

code:
#include "scriptLibrary.js"
drawLine( pt(0,0,0), pt(10,10,0) );


by using an external scriptLibrary.js file:
code:
function pt(x, y, z) {
	var pt = moi.vectorMath.createPoint( x, y, z );
	return pt;
}

function drawLine(pt1, pt2) {
	var factory = moi.command.createFactory( "line" );
	factory.setInput( 0, pt1 );
	factory.setInput( 1, pt2 );
	factory.commit();
}


or a circle:
code:
function pt(x, y, z) {
	var pt = moi.vectorMath.createPoint( x, y, z );
	return pt;
}

function drawCircle(orientation, center, radius) {
	switch (orientation) {
	case "Top":
		var frame = moi.vectorMath.createTopFrame();
		break;
	case "Front":
		var frame = moi.vectorMath.createFrontFrame();
		break;
	case "Right":
		var frame = moi.vectorMath.createRightFrame();
		break;
}
	
	frame.origin = center;
	var factory = moi.command.createFactory( 'circle' );
	factory.setInput( 1, frame );
	factory.setInput( 3, radius );
	factory.commit();
}

drawCircle("Front", pt(0,0,0), 100);


I can see many factories simplyfied like this and not neccessarily a need for an additional simplyfied scripting layer that would break backwards compatibility.
  Reply Reply More Options
Post Options
Reply as PM Reply as PM
Print Print
Mark as unread Mark as unread
Relationship Relationship
IP Logged

Previous
Next
 From:  bemfarmer
5493.17 In reply to 5493.6 
Hi Michael,
I'd forgotten about this old subject, but have a question.

Rather than dragging the marker point of the seam, shown during Loft, is it possible to just enter a point, or coordinates or object list of a previously picked
point on the curve for, say, the orientations list input of Loft, or say the EditOrientations.js?

I'm trying to script changing the start point of an ellipse, using the loft method that has been previously posted.
http://moi3d.com/forum/index.php?webtag=MOI

- Brian

EDITED: 4 Feb 2018 by BEMFARMER

  Reply Reply More Options
Post Options
Reply as PM Reply as PM
Print Print
Mark as unread Mark as unread
Relationship Relationship
IP Logged

Previous
Next
 From:  Michael Gibson
5493.18 In reply to 5493.17 
Hi Brian,

> Rather than dragging the marker point of the seam, shown during Loft, is it possible to just enter
> a point, or coordinates or object list of a previously picked
> point on the curve for, say, the orientations list input of Loft, or say the EditOrientations.js?

So you mean in your own script that you're making, not typing in coordinates in the regular Loft command, right?

I'm not sure if that's possible currently - one thing you can try though is if you run .update() on the Loft factory, the curve orientation input (input index 1 on the loft factory) should get filled in with a default orientation list. It should then be possible to modify that list, you can get it I think by factory.getInput(1).getValue(); that will be a list object, each item in the list is a CurveOrientation object which has 2 properties: flipped and seam which can be modified.

The seam point though is a normalized parameter value, with 0.0 meaning the start of the original curve and 1.0 meaning the end of the curve, and 0.5 meaning the middle of the curve's parameter space, not necessarily the middle of the arc length distance of the curve.

- Michael
  Reply Reply More Options
Post Options
Reply as PM Reply as PM
Print Print
Mark as unread Mark as unread
Relationship Relationship
IP Logged

Previous
Next
 From:  bemfarmer
5493.19 In reply to 5493.18 
Thank you Michael.

I'll do some tests.

I guess that the "curve's parameter space" has to do with the NURBS representation?

- Brian

Using cPlane at the centerpoint, I'm intersecting the "waist" of an extruded (or lofted) pair of circles, (an oblique cylinder), with
a plane, which is a "belt" ellipse. (Like a person with a belt around the waist.)
The ellipse formed often has a different start point than the starting cylinder. I'm trying to move the start point to match the cylinder seam.
It is easy interactively, with a specific cylinder...
  Reply Reply More Options
Post Options
Reply as PM Reply as PM
Print Print
Mark as unread Mark as unread
Relationship Relationship
IP Logged

Previous
 From:  Michael Gibson
5493.20 In reply to 5493.19 
Hi Brian,

> I guess that the "curve's parameter space" has to do with the NURBS representation?

Yup, there is a range of numbers called the "knot vector" which sets a minimum and maximum value for the parameter space range. Evaluating the curve at the start parameter yields the start point of the curve, evaluating the curve at the end parameter gives the end point of the curve.

- Michael
  Reply Reply More Options
Post Options
Reply as PM Reply as PM
Print Print
Mark as unread Mark as unread
Relationship Relationship
IP Logged
 

Reply to All Reply to All

 

 
 
Show messages: All  1-11  12-20