views:

45

answers:

4

I need some help! I have no doubt this is a dumb problem that I've just over-thought to the point I got dumb about it.

I've got one "main" instance of a MovieClip symbol (let's call it Mountain) with an accompanying class. In the flow of the program, I automatically generate 8 other instances of the same symbol, let's say, each has a different fill color. When i click one of those automatically generated ones, I wanted the main instance to change color to whatever color the automatically generated one was.

So after dynamically generating the item in a different class, I added an eventListener for MouseClick

var thisMountain=new Mountain; 
thisMountain.ChangeColor();
thisMountain.addEventListener(MouseEvent.CLICK, itemClicked);
this.addChild(thisMountain);

But that's when I realized that the eventListener had no way to tell the function it's calling, WHICH instance of the symbol was clicked on. So I went and added the event listener into the "Mountain" class, but then it's being called even when the main one is clicked on. So I added a boolean when the instance is created to differentiate, but that seems like awful awful coding.

So what should I do? Is that example clear? Should I just make yet ANOTHER class that extends the mountain class or something? What is the best way to go about doing this?

+3  A: 

You could do something like:

item1.addEventListener(MouseEvent.CLICK, itemClicked);
item2.addEventListener(MouseEvent.CLICK, itemClicked);
item3.addEventListener(MouseEvent.CLICK, itemClicked);
...
...
function itemClicked(e:MouseEvent):void{
 trace((e.currentTarget as MyInstances).myColor);
}

but if you were creating the items in a separate class and didn't know the instance, or how many were created etc. etc. You might like to look into 'Custom Events'. Your items when clicked would fire off an event something like the following.

var myItemClickedEvt:MyCustomEvent = new MyCustomeEvent("itemClicked", myColor);

You could then listen for the "itemClicked" event and then doing something like:

function itemClicked(e:MyCustomeEvent):void{
     trace(e.myColor);
}

... but I'm probably just confusing the situation... you probably just need:

(e.currentTarget as MyInstances).myColor
Trevor Boyle
God y'all all had the same answer, and that was "you never knew about "currentTarget", moron!!! Sorry I could only choose one answer or I'd have clicked 'em all. Thanks a lot y'all
Cyprus106
+2  A: 

just add an id variable to your mountain class:

var thisMountain=new Mountain('id1'); 
thisMountain.ChangeColor();
thisMountain.addEventListener(MouseEvent.CLICK, itemClicked);
this.addChild(thisMountain);
function itemClicked(e:MouseEvent):void{
    trace((e.currentTarget as Mountain).id);
}
www0z0k
+1  A: 

Maybe I'm not understanding your scenario, but why couldn't you just use the event.target property? Is it not what you need? Assuming that Mountain extended a DisplayObject, you should have a reference to the object in question.

Eg:

thisMountain.addEventListener(MouseEvent.CLICK, function(evt:MouseEvent):void {
    // do something with evt.target;
});
mway
+1  A: 

Not a dumb problem, but luckily there's an easy solution:
Use the target property of the MouseEvent.
So your event handler would look something like this:

protected function itemClicked(e:MouseEvent):void {
    var clickedMountain:Mountain = e.target as Mountain; // cast target as a Mountain
    var mountainColor:Color = clickedMountain.mountainColor;

    // do something here to set the color of the main mountain
}

Depending on how your Mountain clip is set up, you might need to use currentTarget instead of target to make sure you're getting the Mountain, and not one of its children.

Cadin