View Full Version : Scripting the Image Name attribute?

04 April 2003, 04:09 PM
I've got a problem. I wan't to script the "Image Name" attribute in a file node to select random image cycles for sprites (not frame extension, which is already scripted).

First of all there is no expression option in the image name attribute. But I tried something like this in the particle runtime exp:

setAttr file1.ImageName = $someCreationExpValue;

I was hoping maybe the hardware renderer would run the runtime expression at the time of rendering each particle, so that I could cheat it, but (of course) it didn't. So it seems it must be done some other way. Does anyone know how?

04 April 2003, 04:42 PM
how about having one long sequence with different image seuences in a row, all the same base name and succeeding numbering?

like that scripting the frame number would be enough..

setAttr does not work with = .. check the docs for the use of it.



04 April 2003, 06:15 PM
Probably the best way to do this is by having a series of textures in an array and then using the rand command to look up the array index randomly:

int $i = `rand 0 100`;
setAttr file1.ImageName myArray[$i];

04 April 2003, 07:03 PM
Unfortunately, David's answer doesn't work if you're doing hardware-textured particle sprites, only if you're treating each sprite as a separate geometry object.

If you look in the Maya documentation under the tempting heading Dynamics : Advanced Particle Topics : Assigning a different image sequence to each sprite you'll see that all they give you is a way to start each sprite on a different frame of one image sequence.

So here's the trick: let's assume your sprite loops are all the same length, say 1000 frames. What you want to do is:

1) Make a SINGLE series of images that contain all of your loops end-to-end. For example, frames 0-999 are the first loop, 1000 - 1999 are the second, and so on.

1) Add the dynamic attribute spriteNumPP to your particles

2) In your creation expression, set the initial value of spriteNumPP like this:

spriteNumPP = rand(0,19) * 1000;
// in this example, we're assuming 20 loops

4) In the runtime expression, update spriteNumPP each frame:

spriteNumPP = (spriteNumPP + 1) % 1000;

This will now pick a random loop for each particle out of the end-to-end sequence of loops that you've put together.

It's a shame there's no better way to do this, but without per-particle filenames (which sprites don't support) this is about the best you can do.

If I were going to do this in production I would consider writing a short install script that would let me take a library full of sprite loops and compile the end-to-end sequence of loops on the fly whenever I made changes. It would use a little more disk space but would be easier to manage that way.

-- Mark

04 April 2003, 08:48 PM old nemesis.... :p

I was reading too quickly and thought it was to randomly assign a texture for a material.

I agree that writing a management tool is the way to go though.

04 April 2003, 08:50 PM
Nemesis? I hope not! :D

-- Mark

04 April 2003, 08:56 PM

sarcasm. Tis a wonderful thing.

04 April 2003, 09:49 PM
Thank you all for replying! Mark: Super! I've got it all working now.

One little thing: spriteNumPP = (spriteNumPP + 1) % 1000;

This does not allow the values to go above 1000. 2900 becomes 900, 1800 becomes 800. That's not a problem, my sprites are driven by a very different expression. I know it's not supposed to do this, but I'm sure you've got a good answer to it ;)

04 April 2003, 09:56 PM
Oops slight mistake, as you noted:

The thing to do is make a second per-particle attribute. You can use one of the userScalar<n>PP attributes. Then, you do something like this:

// creation expression
spriteNumPP = rand(0,19) * 1000;
userScalar1PP = spriteNumPP;

// runtime expression
spriteNumPP = (spriteNumPP + 1) % 1000 + userScalar1PP;

This should fix your problem. Now, each particle will cycle through the range of frames for its particular sprite loop.

-- Mark

04 April 2003, 12:24 PM
Thank you for clearing that up Mark.

Then, you do something like this:

Just for future reference. One would have to do this in the creation expression:

// select random loop
int $randLoop = rand (0,19);
$randLoop *= 1000;
userScalar1PP = $randLoop;

// select random sprite in loop
int $randSprite = rand (0,1000);
spriteNumPP = $randLoop + $randSprite ;

Runtime is ok.

04 April 2003, 04:46 PM
mmi: sorry, you hadn't made it clear that you wanted the particles with the same loop to be out of phase with each other. I could imagine that going either way depending on what you're trying to do, but I can see why in most cases you'd want it that way.

-- Mark

04 April 2003, 01:08 PM
Yes, you're right. I didn't mean to correct you, just show what I needed to do for my specific task :)

CGTalk Moderation
01 January 2006, 10:00 PM
This thread has been automatically closed as it remained inactive for 12 months. If you wish to continue the discussion, please create a new thread in the appropriate forum.