Jump to content
Developer Wiki and Function Reference Links ×

global variables in a marionette script


DomC

Recommended Posts

Hi

 

I am not sure what is best practice to script a complex scripting-project in Vectorworks.

 

For me a Marionette Script hast the big advantage, that I have a kind of visual pattern to unterstand the script also to launch other users into a scripting project. Also I got the experience, that I can't understand one of my own scripts I did weeks ago which I did not create a very detailed documentation and which are just text based. But I can unterstand my old Marionette Scripts after some minutes of induction. Even if there are custom nodes the Marionette container is still a powerful and visual organization tool for scripts. So it try to do scripts as long as possible in a Marionette class. 

 

For complex projects it can be reasonable to code a Classic-Script or outsource some content in external resources. Just to reduce the number of nodes and the complexity of the wire system. Also sometimes it feels noobish to  create the same functions in different nodes and lead values from the start of the scripts kilometers to the end of a script. 

 

So I searched a way to create global functions(methods) and global values for a script. There are different ways:

 

1. Create external Python module and use them as an instance to use it in every python script or marionette script

The Big minus for that is, that resources have to be transported from one computer to the next or have to be checked/installed by the script itself.

 

2. Create global functions and global values inside the Marionette network. 

 

It tried the following, which work:

 

1. define globals in the first possible node in the network, which has to be wired to all nodes which wants to use the globals.

# Example:
global test
test =  'This is a global variable'

global globalFunction
def globalFunktion():
  vs.Message('global Function sucessful called')
  
  
#or this way This will create a Resource list which can be used in all connected nodes

Marionette.Symbole = vs.BuildResourceListN(16,path)
Marionette.Texturen = vs.BuildResourceListN(97,path)

#My original code defines as example functions to import resources in the document if they are needed. And should prevent of creating or #wiring a resource list in every node the resource are needed.

	import vs
	import xml.etree.ElementTree as ET
	path = self.Params.inPath.value+'/'+self.Params.file.value
	tree = ET.parse(path)
	root = tree.getroot()
	
	
	raumDefinition = []; Moebel = []; Produkt =[]
	
	for child in root:
		t = child.tag
		
		if t == 'raumDefinition':
			raumDefinition.append(child)
		if t == 'Moebel':
			Moebel.append(child)
		if t == 'Produkt':
			Produkt.append(child)


	path = self.Params.inPath.value+'/'+'3D Daten.vwx'

#####globals start

	Marionette.Symbole = vs.BuildResourceListN(16,path)
	Marionette.Texturen = vs.BuildResourceListN(97,path)
	

	global texturMaker
	def texturMaker(requested_textures):
	
		res_list, n = Marionette.Texturen
		for item in requested_textures:
			for i in range(n):
				n = vs.GetNameFromResourceList(res_list, i)
				if item in n:
					s = vs.ImportResourceToCurrentFile(res_list, i)
	
	def symbolMaker(requested_symbols):
		res_list, n = Marionette.Symbole
		for item in requested_symbols:
			for i in range(n):
				n = vs.GetNameFromResourceList(res_list, i)
				if item in n:
					s = vs.ImportResourceToCurrentFile(res_list, i)
#####globals end

	
	self.Params.raumDefinition.value = raumDefinition
	self.Params.Moebel.value = Moebel
	self.Params.Produkt.value = Produkt

595ffddaca866_Bildschirmfoto2017-07-07um23_31_57.png.98552c11ee652153852feb2add1c8967.png

 

Can somebody see any issues by doing this? Or maybe can see a better way? 

Is it better to use the global keyword or is it better to write the variable into the Marionette class?

 

 

 

 

 

Edited by DomC
Link to comment
  • 4 weeks later...

Hi Dom,

 

handling global vars looks like a dangerous thing to me.

You have to be very carefull when connecting the nodes because it can change the flow of the network (first connected -> frist executed)

which may lead to inconsistent values. (global var is accesed before assigned...).

 

It seems that the flow also depends on the node from which you run the network.

 

I've attached an example.

 

regards

 

 

 

global_var_test_v2017.vwx

  • Like 1
Link to comment
  • Marionette Maven

I would like to second @Patrick Winkler's opinion on this.

I'd also like to say that Patrick's assumption on where the network flow begins is accurate to a degree, from what I've learned from smarter beings than myself. This could (and likely will) introduce problems when networks are non-linear and branch off. I also have very little understanding on where networks begin from when wrapped, so using wrapper nodes could also introduce problems.

  • Like 1
Link to comment

You are right

 

The Connection order influences the order of node execution, so this is not a reliable solution. Maybe the proper way is to create a python wheel package which provides custom modules to the Marionette script. Or leave it Marionette stile and deliver the functions/values through the visible wires. Wireless Node connections ... hm ... somehow cut across the idea of visual scripting :-)

 

Thanks for Feedback

Dom

 

 

 

Link to comment

Just in addition

As so often ... good things are already there.

#COMMAND;REFFILE;[VWLibDef]/DomC\TheNode.py;

While this will not optimize speed and reduce number of node-classes in the generated python script, but at least the wish is granted, to keep nodes synced and up to date. Also this will work, if the file reference does not exist the file will be automatically created after edit the respective node.

Link to comment

I've changed the Marionette.py to make it capable of showing the exceution order.

I think this can also be helpfull in other cases then global var handling.

 

You have to replace the Marionette.py inside the marionett plugin by the attached one (on your own risk).

It only shows the order on the first outport if there is a vw class named 'mrnt_show_order' in the doc otherwise it shows the number of output values as usual.

 

598db3a9efe2c_Bildschirmfoto2017-08-11um15_35_39.png.6af19a8dae51ca03a085d4161fad5a2e.png

Marionette.py.zip

Edited by Patrick Winkler
  • Like 1
Link to comment

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...