Notifications
Clear all

[Closed] Run an MCR file but ignore its macroscrip header?

I wonder, out of curiosity; Is it possible to run an MCR file but ignore the macroscript header, ie only read what is between ( and ) ?

I assume that one dont want to evaluate the whole macroscript over and over again, or is it harmless?

35 Replies
1 Reply
(@denist)
Joined: 10 months ago

Posts: 0

see macros.run

or do you need something different?

mcr without its header is just a script.

2 Replies
(@haider_of_sweden)
Joined: 10 months ago

Posts: 0

Yes, I understand this. But I needed to know if there were downsides reevaluating MCRs over and over compared to evaluating MS files.

Would you please elaborate this?
Does it mean things outside “on execute” will not be reevaluated, just what’s inside or the other way around?
If so, does it mean an script structured as an MCR is partially read on an evaluation compared to an MS that is fully evaluated?

Let me just quickly explain why this question came to my mind.
There are scripts out there that generate menus or popups or in some way list up all available scripts in a user interface. By some reason, the MCRs are ignored.
So I assumed that the MCR part, the macroscript plus on execute handler which are additions on top of a regular MS file might be the reason. And if so, I wondered if there was a way to strip away those parts on the fly and read the MCR just like if it was an MS file.

(@swordslayer)
Joined: 10 months ago

Posts: 0

Exactly, here’s a minimal example to show that:

macroscript ScopeExample
(
	local counter = 0
	on execute do print (counter += 1)
)

Run it a few times with macros.run #unknown #ScopeExample and see the value increasing. Basically, the on execute scope is meant for things that happen on executing the macro, the top-level scope for initialization of the macro, functions, rollout definitions and stuff like that.

In that case those scripts are poorly written. Use macros.list (for example macros.list to:stringStreamToParse) to get all the macros, avoid what you suggested… Like, really

The only difference is when there’s a on execute handler, in that case what’s outside of it is persistent across session, what’s inside is what gets reevaluated. So in case that the person writing it used the macroscript top-level scope to store values across multiple runs, that will break.

Sorry for bumping up this thread, but I realised I had still an unanswered question.

When I run fileIn ((getdir #userMacros)+"\somefile.mcr"), the Macroscript gets evaluated as expected.
How can I run the macroscript-file but ignoring the header and only running the script inside it?

Separate the headerd in .mcr(header.mcr) file and the body of the script in .ms(body.ms or body.mse) file. When you want to evaluate the macro fileIn the header.mcr, when you want to load the real script fileIn body.ms

Thanks @miauu . This I know, but I was hoping there was a way to do this scriptwise without altering the original MCR-file. Something like runAsScript(macroScript.mcr) and then have it only run what is between the first and last parenthesis-signs…

You can read .mcr file as string with something like this (dotnetclass “System.IO.File”).ReadAllText and remove the macroscript definition header
And of course it doesn’t guarantee that this altered string can be executed via Execute function without errors.

macros.run works if you have evaluated the Macroscript already.
I need something different, more like what @Serejah is mentioning.

The logic could be like this

  1. read the macroscript-file as text
  2. search for the string macroscript and then it searches for the first (
  3. Execute everything from ( to the end of the file.

There might be a bunch of commented text before the macroscript header starts, for example author notes with the word “Macroscript” followed by a paranthesis that has nothing to do with the macroscript. A solution could be that to ask the user for confirmation

Do you want to execute the code within "macroscript Macroname tooltip:"blah blah" text text text"

ie, it shows you a preview of the first macroscript row to let the user confirm we found the correct macroscript start. If not, the user can press "search next".

Once you find the right spot, you can press Run the execute the code inside the Macroscript without executing the header.

I doubt that it would be that easy.
How about macro with such structure?

macroScript testmacro
buttonText:"testmacro"
category:"custom"
tooltip:"test macro"
icon:#("someicon",1)
(
	local state = off
			
	fn someFunction = (

		...

	)
	
	
	on isChecked do
	(
		state
	)
	
	on isEnabled do (
				
		enabled = isKindOf selection[1] Editable_Poly
		if not enabled do state = false
		enabled
		
	)

	on execute do
	(
		...
		someFunction()
		...
	)
)

@Serejah, the problem I am facing here is that as long you execute a Macroscript, you’ll have a copy of it under $userScripts.
If you decide to test out bunches of scripts, you’ll end up with a heap of files and categories that needs to be cleaned up manually .

Maybe we could save out a temporary .ms file and then run that file.

Page 1 / 3