Skip to Content

How to drag and drop in Flash

Author: Bill Trikojus

 
1

Document setup

 
2

Actions

 
3

Create a target

 
4

Positioning within a target

 
5

Drag multiple objects

 
 
 
 
1

Document setup

 
 


OK here is a drag and drop tutorial for Flash MX. The finished movie should look like this -


Start by opening Flash. Make a new file and set the Frame rate to 21.
Draw a circle.
Select the circle and hit F8 to convert it to a Movie Clip (MC) - name it circle_mc.

Convert to symbol

Also give the circle_mc on the stage an instance name of circle_mc.

instance name

Make a new Layer and name it "actions"

On frame 1 of the actions layer put this -

circle_mc.onPress=function(){
startDrag(this);
}
circle_mc.onRelease=circle_mc.onReleaseOutside=function(){
stopDrag();
}


OK now save your movie as dragndrop.fla and go Control/Test Movie.

You should be able to drag your cicle around - if you can't then you've done something wrong.

 
2

Actions

 
 


OK underneath the action actions you already have on frame 1 add this - //the variables below will store the clips starting position

circle_mc.myHomeX=circle_mc._x;
circle_mc.myHomeY=circle_mc._y;

circle_mc.onMouseDown=function(){
//this variable tells us if the mouse is up or down
mousePressed=true;
}
circle_mc.onMouseUp=function(){
mousePressed=false;
}
circle_mc.onEnterFrame=function(){
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)
if(mousePressed==false){
this._x-=(this._x-this.myHomeX)/5;
this._y-=(this._y-this.myHomeY)/5;
}
}


Paste this into flash and then have a read of the code comments.

OK test your movie again and you will see that you can drag your circle around but when you let go of the mouse the circle moves back to its starting position with a smooth motion.

 
3

Create a target

 
 


OK now we want to check where the circle is bring dropped. Start by creating a new layer and dragging the new layer below the layer that has the circle_mc on it. Now draw a big circle down the bottom right hand corner of the stage. Select the circle you have just drawn and convert it to a movie clip - name it target circle and give it an instance name of targetCircle. Double click on the target MC to go inside it. Put a stop action on both first and second frames. Create a new keyframe for the circle in frame 2 (hit F6) and give it a different fill colour.

Now go back to the main timeline and change the onRelease actions to this -

circle_mc.onRelease=circle_mc.onReleaseOutside=function(){
stopDrag();
if (this._droptarget == "/targetCircle") {
this.onTarget=true;
_root.targetCircle.gotoAndStop(2);
}else{
this.onTarget=false;
_root.targetCircle.gotoAndStop(1)
}
}


and the if statement in the enterFrame actions to this

if(mousePressed==false&&this.onTarget==false){

Still with me? Ok test the movie again and watch what happens when you drag the circle around - both on and off the target.

 
4

Positioning within a target

 
 


OK what else?? hmm maybe when we drag the circle on to any part of the target, we want the circle to move to the center of the target. Ok let's do that.

Change all the actions on frame 1 to this -

circle_mc.onPress = function() {
startDrag(this);
};
circle_mc.onRelease = circle_mc.onReleaseOutside=function () {
stopDrag();
if (this._droptarget == "/targetCircle") {
this.onTarget = true;
_root.targetCircle.gotoAndStop(2);
} else {
this.onTarget = false;
_root.targetCircle.gotoAndStop(1);
}
};
//the variables below will store the clips starting position
circle_mc.myHomeX=circle_mc._x;
circle_mc.myHomeY=circle_mc._y;
//the variables below will store the clips end position
circle_mc.myFinalX = targetCircle._x;
circle_mc.myFinalY = targetCircle._y;
circle_mc.onMouseDown = function() {
//this variable tells us if the mouse is up or down
mousePressed = true;
};
circle_mc.onMouseUp = function() {
mousePressed = false;
};
circle_mc.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (mousePressed == false && this.onTarget == false) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (mousePressed == false && this.onTarget == true) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};

Test the movie again and watch what happens (or look away and cross your fingers - it's up to you...).

 
5

Drag multiple objects

 
 


Now the code above if fine if you just want to drag and drop one object, but things can get pretty messy if want to be able to drag multiple around. So, rather than just duplicate the code we already have for each mc, lets make a function that will give an mc the drag and drop functionality you have already seen. Copy the function below and replace all the code on frame 1 of your movie:

function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}


So now we have a function that we can call to setup as many dragable objects as we want. When you call the function you must provide 2 parameters - the clip that you want to be dragable and the target for that clip. Add this to the bottom of your code

dragSetup(circle_mc,targetCircle);

Using this function will keep your code much cleaner when dragging multiple objects. Option drag out a copy of targetCircle and circle_mc and change the copies instance names to targetCircle2 and circle2_mc. Now to give circle2_mc the same functionality as circle_mc, all you have to do is add this line of code

dragSetup(circle2_mc,targetCircle2);

Much cleaner than duplicating all that code!!

You can download the finished source files for this tutorial here.

You can also download the finished source file in Actionscript 3 here

 To learn more about dragging and dropping in Actionscript 1.0 check out 'ActionScript for Flash MX: The Definitive Guide' by Colin Moock.
 

bulletBack


Share

Like this? Click a link below to share it...


Subscribe and Download

Subscribe to the Swinburne Faculty of Design Podcasts

Comments

2008-04-12: Dustin Lafleur said:
I am attempting to use this code in a multiple drag and drop situation. I would like to use the following section of this code but it does not seem to work when dealing with multiple objects.

if (eval(this._droptarget) == targ) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}



2008-04-13: Bill Trikojus said:
in the dragSetuo function try adding an extra line where the position variables are set

clip.targ=targ;


then in the if statement you posted above try

if (eval(this._droptarget) == this.targ) {

--------
iStaySafe - Emergency App for iPhone


2008-04-24: Albert said:
Hello, your tutorial is realy-realy great! Also your explanation of multiple drag and drop situation. But I have problem what I can't figure out. In my application what I trying to write you can drag and drop letters to 14 targets. But the letters must snap on the targets, not a big problem you will think. ;-) But you can drop each letter of one of the 14 targets. So you can drop the letter "E" on the first target but also on the second, third, and so on targets.

Still with me? ;-)

Do you know a sollution to my problem?

2008-04-24: Bill Trikojus said:
You can snap a dragged object to the clip it is dropped on by checking the _droptarget

eg

someClip.onRelease=function(){
stopDrag();
theClipIWasDroppedOn=eval(this._droptarget);
this._x= theClipIWasDroppedOn._x;
this._y= theClipIWasDroppedOn._y;

}



Hope that helps
--------
iStaySafe - Emergency App for iPhone


2008-04-25: Albert said:
Wow that's great and just what I was looking for! Is there also a way to achive some smoothness, like the way you show in your example?

I have come up with this solution but that wouldn't work. :-P
letter_a.onRelease=function(){
stopDrag();
theClipIWasDroppedOn=eval(this._droptarget);
this._x= (theClipIWasDroppedOn._x)/5;
this._y= (theClipIWasDroppedOn._y)/5;
}

2008-04-25: Bill Trikojus said:
on the right track but you need to start an enterframe script to make it ease to the target

eg


letter_a.onRelease=function(){
stopDrag();
theClipIWasDroppedOn=eval(this._droptarget);
this.onEnterFrame=function(){
this._x-= (this._x-theClipIWasDroppedOn._x)/5;
this._y-= (this._y-theClipIWasDroppedOn._y)/5;
}
}


If you are using Flash 8 or 9 check out the Tweener class - makes easing easier

cheers
--------
iStaySafe - Emergency App for iPhone


2008-05-08: Dustin Lafleur said:
Thanks Bill,

Your help was very useful.

I do have another question though. Is it possible to re purpose this code so that a single movie clip can have dual targets.


2008-05-08: Bill Trikojus said:
Sure. Just add another parameter to the function

function dragSetup(clip, targ1,targ2) {


then check both targets when you drop the clip

if (eval(this._droptarget) == targ1 || eval(this._droptarget) == targ2) {



|| means OR

cheers
--------
iStaySafe - Emergency App for iPhone


2008-05-20: curtis redden said:
This is really good, but how do i make it so that when the correct target is chosen it can play a movie clip once object is dropped?

Like when the user drops the object onto the wrong target it will explode or something like that. how do i do this

2008-05-20: Bill Trikojus said:
Well in the onRelease you have

if (eval(this._droptarget) == targ) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}


just add another gotoAndPlay in there. Assuming that the movieclip you want to play is the one being dragged, and assuming that you have a couple of frame labels set up inside that movieclip, it would be something like

if (eval(this._droptarget) == targ) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
this.gotoAndPlay('correct');
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
this.gotoAndPlay('incorrect');
}

cheers
Bill
iStaySafe - Emergency App for iPhone
--------
iStaySafe - Emergency App for iPhone


2008-05-21: Dave said:
Hi,
I use this AS in a clip and it wasn't dropped on my target. I put this lines:

clip.targ=targ;
if (eval(this._droptarget) == this.targ)

It targets but now the circle doesn't move back. This is my code:

clip.targ=target;

case_gratuit_mc.onPress = function() {
startDrag(this);
case_gratuit_mc.gotoAndPlay(2);
};
case_gratuit_mc.onRelease = case_gratuit_mc.onReleaseOutside=function () {
stopDrag();
case_gratuit_mc.gotoAndPlay(1);

if (this._droptarget == this.targ) {
this.targ = true;
case_gratuit_mc.gotoAndPlay(3);
//targetCircle.gotoAndStop(2);
} else {
this.targ = false;
//targetCircle.gotoAndStop(1);
}
};
//the variables below will store the clips starting position
case_gratuit_mc.myHomeX=case_gratuit_mc._x;
case_gratuit_mc.myHomeY=case_gratuit_mc._y;
//the variables below will store the clips end position
//circle_mc.myFinalX = 443;
//circle_mc.myFinalY = 294;
case_gratuit_mc.onMouseDown = function() {
//this variable tells us if the mouse is up or down
mousePressed = true;
};
case_gratuit_mc.onMouseUp = function() {
mousePressed = false;
};
case_gratuit_mc.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (mousePressed == false && this.onTarget == false) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (mousePressed == false && this.onTarget == true) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};


Thx for some help.

2008-05-21: Bill Trikojus said:
not sure what you are trying to do that is different to the tutorial but there is definately issues with your targ variable - at one point it is a movieclip and another it is a boolean (true or false);

trace targ in your on release


case_gratuit_mc.onRelease = case_gratuit_mc.onReleaseOutside=function () {
stopDrag();
trace(this.targ)
trace(this._droptarget);

case_gratuit_mc.gotoAndPlay(1);
//here the targ var is a movieclip
if (this._droptarget == this.targ) {
//and here it is a boolean - so which is it? Should this be onTarget?
this.targ = true;
case_gratuit_mc.gotoAndPlay(3);
//targetCircle.gotoAndStop(2);
} else {
this.targ = false;
//targetCircle.gotoAndStop(1);
}
};

If you can't get it working please post it on actionscript.org .
--------
iStaySafe - Emergency App for iPhone


2008-05-24: Monte said:
This is a GREAT tutorial. Exactly what I was looking for. My question is about integrating a Tween class into this code.

I usually use TweenLite, but I was going to test with the included Macromedia Tween class and got a syntax error just trying to import it into the code.

I want to use the Tween class to send the clip back to starting position with an Elastic or Back ease, and the successfully dragged clip will Alpha to zero and move off screen (say, _x:1000).

How would this work and what code to replace?

Thanks again!

2008-05-24: Bill Trikojus said:
well I'm I'm not sure why you are getting that syntax error but you should check out the new easing tutorial I just made.

The code to integrate the Tween class would look like this

import mx.transitions.Tween;
import mx.transitions.easing.*;


function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);

};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();

if (eval(this._droptarget) == targ) {
var tx:Tween=new Tween(this,'_x',Elastic.easeOut,this._x,this.myFinalX,1,true);
var ty:Tween=new Tween(this,'_y',Elastic.easeOut,this._y,this.myFinalY,1,true);
targ.gotoAndStop(2);
} else {
var tx:Tween=new Tween(this,'_x',Elastic.easeOut,this._x,this.myHomeX,1,true);
var ty:Tween=new Tween(this,'_y',Elastic.easeOut,this._y,this.myHomeY,1,true);
targ.gotoAndStop(1);
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;

}

dragSetup(circle_mc,target_mc)


Also see attached drag and drop with tween class example.

cheers
Bill
iStaySafe - Emergency App for iPhone
--------
iStaySafe - Emergency App for iPhone


2008-05-29: Laura Sullivan said:
Thanks Bill, Thats been really helpful.
My problem is kind of complicated, i have applied the tutorial to parts of my animation and it has worked a treat! thanks!
my problem comes in two parts
the target needs to be the result of a movie clip, which is activated on press of the item to be dragged.
so i've got the item moving, i just cant work out how to get it to activate the movie clip and target

the other part is the same, except that the item to be dragged is revealed at the end of another movie clip being played.
i have the item appearing fine, and it shows an active link when rolled over but i cant get the code to apply to it..

is such a request feasible or should i just simplify the scene?

2008-05-29: Bill Trikojus said:
Hi Laura

I'm not sure I understand the issue here but to activate the 'drag-ability' of one movieclip when another is clicked and drag you could do something like this

movieclip1_mc.onPress=function(){
this.startDrag();
dragSetup(movieclip2_mc,target_mc)

}

Does that make sense? You just delay calling the dragSetup function until the first movieclip is clicked

cheers
Bill
iStaySafe - Emergency App for iPhone
--------
iStaySafe - Emergency App for iPhone


2008-06-06: Gerald Kaute said:
Hi. I can't see my post here so Ill repeat it.

I copied the code into the root and most stuff works BUT the target bit doesn't - ie: Doesn't stop dragging.

//onClipEvent (enterFrame) {
stop();
dragSetup(_root.hamburger2,_root.box1);
dragSetup(_root.hamburger1,_root.box1);
function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ) {

this.onTarget = true;
gotoAndPlay(2);
} else {
this.onTarget = false;
trace(failure);
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;

}

};

}

2008-06-06: Bill Trikojus said:
Code looks fine. You may have a depth issue that is preventing the onRelease from firing when you have dragged over the target
--------
iStaySafe - Emergency App for iPhone


2008-06-11: Chris said:
hey, this is really nice, but what I need to do is the following:

I have a true false quiz with five questions. Next to each question is a box. Off to the side are two draggable boxes, one labeled true, the other false. How do I use multiple instances of the same boxes so that the user can drag the corrosponding answer to the correct box next to each question??? I'm also looking for some kind of feed back that gives the user two attempts at the question.

Thanks in advance for your help.

2008-06-11: Bill Trikojus said:
The dragSetup function is designed to exactly what you are describing in the first part of your question - that is assign drag and drop to multiple instances (can be instances of the same movieclip) and assign them different targets. So you should just be able to say

dragSetup(true1_mc,target1_mc);
dragSetup(false1_mc,target1_mc);
dragSetup(true2_mc,target2_mc);
dragSetup(false2_mc,target2_mc);
//etc

regarding the 2 chances (which seems a little strange given that this is a true or false quiz but anyway) you could create a counter in each target that tracks how many attempts have been made. I would need to see all your quiz code but it would be something like


function dragSetup(clip, targ) {

//start counter
targ.numAttempts=0;
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ) {

//you need your own code here to determine if answer was correct or not
if(answerCorrect && targ.numAttempts<2){
this.onTarget = true;
_root.targ.gotoAndStop(2);

}else{
targ.numAttempts++

}

} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}



cheers
--------
iStaySafe - Emergency App for iPhone


2008-06-24: Gerald Kaute said:
All works well on its own but NOT when loaded into another movieclip.

trace(eval(this._droptarget)); is undefined when I load this into an emptymovieclip called container_mc2

stop();


fscommand ("fullscreen", "true");
fscommand ("showmenu", "false");
fscommand ("allowscale", "TRUE");

this._lockroot = true;

_root.createEmptyMovieClip("Background_mc", _root.getNextHighestDepth());
_root.soundBG = new Sound(Background_mc);
_root.soundBG.loadSound("BGmusic.mp3" , true);
_root.soundBG.start(0, 999999);
_root.soundBG.setVolume(30);


dragSetup(_root.cat_mc,_root.catShadow_mc);
dragSetup(_root.dog_mc,_root.dogShadow_mc);
dragSetup(_root.bird_mc,_root.birdShadow_mc);
dragSetup(_root.cow_mc,_root.cowShadow_mc);
// dragSetup(_root.circle2,_root.box1);
// dragSetup(_root.hamburger1,_root.box2);
function dragSetup(clip, targ) {
clip.onPress = function() {

startDrag(this);

//_root.createEmptyMovieClip("objectSound_mc");
//_root.objectSound = new Sound(objectSound_mc);
//var sound:String = clip;
//var aFile:String = "/sounds/" + sound + ".mp3";
//_root.objectSound.loadSound( aFile, 0 );
//trace(aFile);
//_root.objectSound.loadSound("/sounds/cat_mc.mp3" , true);
//_root.objectSound.start(0, 999999);
//_root.objectSound.setVolume(100);
//_root.createEmptyMovieClip("objectSound_mc",-1)


this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
trace(eval(this._droptarget));
trace(targ);

if (eval(this._droptarget) == targ) {

this.onTarget = true;
trace("yeah");
}
}
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;

}
}
}
var mouseListener:Object = new Object();
mouseListener.onMouseMove = function(){
crosshair._x = _xmouse;
crosshair._y = _ymouse;
};
Mouse.hide();
Mouse.addListener(mouseListener);

2008-06-24: geraldkaute said:
Yes, I forgot to say that somebody mentioned lockroot - but that doesn't solve the prob although its supposed to. Also something about _parent.
I can't make it work.

2008-06-24: Bill Trikojus said:
Yes lockroot should fix it. What version of flash are you publishing as? In any case, it is better to fix the actual problem which is the absolute paths - these need to be made relative (straight to the object you are targeting).

eg

//absolute path
dragSetup(_root.cat_mc,_root.catShadow_mc);

//relative path
dragSetup(cat_mc,catShadow_mc);

//relative path
dragSetup(_parent.cat_mc, _parent.catShadow_mc);



not sure which relative path is correct (if either) but the point is you need to provide the path directly from the location of the code to the object you wish to target

hope that helps

cheers


Bill
iStaySafe - Emergency App for iPhone
--------
iStaySafe - Emergency App for iPhone


2008-07-01: Silverkrown said:
Thanks for the code. How would I change it so there is no color change just the drop target. I want them to be able to drag the image and if it isn't in the correct area snap back but if it is in the correct drop area just stay there? Sorry if this doesn't make sense but I am new to flash. Also it has to be relative, I can't call the root.

2008-07-01: Bill Trikojus said:
to remove the colour change jusr get rid of

_root.targ.gotoAndStop(2);

to make that relative just get rid of _root

Lots of tutes available on paths - couple of good ones on actionscrpt.org

cheers
--------
iStaySafe - Emergency App for iPhone


2008-08-05: loop said:
I want a button with onRelease and if clip = dropped on targ1 , punten_txt++ How do I do that?

2008-08-20: Oliver Allen said:
Hi. Really awesome tutorial!

I have been trying to acheive the same as Dustin Lafleur in regards to multiple targets. I would like to be able to drag an object across the stage and have it move to the centre of whatever target it is currently over (like in the tutorial) but with multiple target areas. (I hope you understand what I mean).

I tried using: doing what you mentioned:

"Sure. Just add another parameter to the function

function dragSetup(clip, targ1,targ2) {


then check both targets when you drop the clip

if (eval(this._droptarget) == targ1 || eval(this._droptarget) == targ2) {"


..but unfortunately it doesn't seem to work at all.

Can you suggest what I may be doing wrong.

Much thanks and appreciation.

Ollie

2008-08-20: Bill Trikojus said:
I have uploaded a drag and drop with multiple targets example - I hope it helps

cheers
--------
iStaySafe - Emergency App for iPhone


2008-08-20: Oliver Allen said:
Thanks Bill, that's great.

Unfortunately I am now having yet another problem: The objects I am dragging are large. I would rather that; if the objects position is within the target when the mouse is released (instead of the mouse release being within the target) then this is when the object will align to the target.

I hope you understand what I mean.

To explain myself further; the targets in my flash file are off the stage therefore a mouse release canot be detected. This is why I need the object's position (on mouse release) to determine which target it is in and will align to.

Many thanks.

Ollie

2008-08-20: Bill Trikojus said:
I'm afraid I don't understand. _droptarget does return the object that the dropped object is touching - it doesn't have anything to do with where the mouse is released. If your targets are all off the stage, I don't see how you can see "if the objects position is within the target when the mouse is released ...then this is when the object will align to the target.". It sounds like you might need to use hitTest() instead of _droptarget

I hope that helps
--------
iStaySafe - Emergency App for iPhone


2008-09-08: Durogista said:
hi bill,

im new to flash and im currently using flash 8 pro. and im having a problem regarding the the object to be dragged. i want the object to be locked inside the target and then create a reset button for it. can u show me how to code it?

thanks in advance bill

Durogista

2008-09-08: Bill Trikojus said:
Hi Durogista

Topics that are quite different to the tutorial should probably be discussed at a forum like actionscript.org because you can upload example files etc. BAsically you need to set some extra parameters in the call to startDrag() that defines the area that the object can be dragged with

All the best
--------
iStaySafe - Emergency App for iPhone


2008-09-20: kay said:
Hi, your tutorials on drag & drop scenarios has been beneficial. However I’m having difficulties trying to reset the dragable objects to there original positions.

Do I need to write a reset function? Can you shed some light on how I do this.

I’ve attached the source code below.

function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
};
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
clip.onEnterFrame = function() {

if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}

dragSetup(circle_mc,targetCircle);
dragSetup(circle2_mc,targetCircle2);



reset1.onRelease = function (){

circle_mc._x = circle_mc.myHomex;
circle_mc._y = circle_mc.myHomey;

}
stop();


Any help I will be greatly appreciated.


2008-09-20: Bill Trikojus said:
You have typos on the var names

eg

circle_mc.myHomex

should be

circle_mc.myHomeX

cheers
--------
iStaySafe - Emergency App for iPhone


2008-09-21: kay said:
Thanks for the swift response, it now works.
What i like to know is, how easy is it to start a animation within the movie clips once it has been drop onto the target.





2008-09-21: Bill Trikojus said:
Kay for some reason your comments are posting multiple times. Please don't refresh the window after posting.

What you want to do is pretty simple. In the dragSetup function, when you have detected that you have dropped on the target, tell the clip taht was just dropped to gotoAndPlay something

eg

if (eval(this._droptarget) == targ) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
this.gotoAndPlay(2);
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}




cheers
--------
iStaySafe - Emergency App for iPhone


2008-09-23: kay said:
Sorry about that, thanks for the information it works, another question. What if I want to target a few more draggable Movie clips, to gotoAndPlay frame 2 without effect the other movie clips frames.

2008-09-24: Bill Trikojus said:
hi Kay

I would need more info such as whether or not you want to target the same clips whenever an object is dropped. Probably best if you post this on a flash forum such as actionscript.org

Cheers
--------
iStaySafe - Emergency App for iPhone


2008-09-26: ziotoo4 said:
Hi Bill!
I have a problem with this script. I see you already gave an answer to my same question, but, since i am a real newbie, i can't get a grip on the solution.
I am trying to make a draggable slider, with 3 stations: Low, medium, and high.
Like this: Low---Med---High.
I have a movie clip that can be moved only on the x axis (horizontally). So far, no problems. But how can i make the slider move to the nearest station when i drop it?
Basically, i managed to understand your code for single target/single MC or N targets/N movie clips...but how can i change it to N targets/1 movie clip? What lines should i change? why?

Please be as clear as you can, cause, as i said before, i'm only 15 Y.O. and therefore i'm a newbie ;-)

Thanks! Fede, from Italy

2008-09-26: Bill Trikojus said:
Hi Fede from Italy

Probably easiest to just check out this drag and drop with snap example.

Hope it helps

cheers
--------
iStaySafe - Emergency App for iPhone


2008-09-26: fede said:
Thanks Bill!
This is perfect, but it has an issue: The moving of the green bar is not smooth: it just skips back to the station. I was able to do so; but the problem was the smooth move....

How can i do to add the tween?
Thanks! Fede

2008-09-26: Bill Trikojus said:
No problem. Check out the easing with actionscript tutorial - should be quite simple to apply the concepts in that to get the bar easing to the target rather than snapping.

Cheers
--------
iStaySafe - Emergency App for iPhone


2008-09-27: Fede said:
Hi Bill; still me. I tried to modify your code because the file you gave me wasn't really what i was looking for.
Now, I have 3 MC: Circle_mc, targetcircle1 and targetcircle2. The code is like this:
circle_mc.onPress = function() {
startDrag(this);
};
circle_mc.onRelease = circle_mc.onReleaseOutside=function () {
stopDrag();
if (this._droptarget == "/targetCircle1") {
this.onTarget = true;
_root.targetCircle1.gotoAndStop(2);
}
else if (this._droptarget == "/targetCircle2") {
this.onTarget2 = true;
_root.targetCircle2.gotoAndStop(2);
} else {
this.onTarget = false;
_root.targetCircle.gotoAndStop(1);
}
};
//the variables below will store the clips starting position
circle_mc.myHomeX = circle_mc._x;
circle_mc.myHomeY = circle_mc._y;
//the variables below will store the clips end position
circle_mc.myFinalX = 450;
circle_mc.myFinalY = 250;

circle_mc.myFinalX2 = 110;
circle_mc.myFinalY2 = 286;
circle_mc.onMouseDown = function() {
//this variable tells us if the mouse is up or down
mousePressed = true;
};
circle_mc.onMouseUp = function() {
mousePressed = false;
};
circle_mc.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (mousePressed == false && this.onTarget == false) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (mousePressed == false && this.onTarget == true) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
else if (mousePressed == false && this.onTarget2 == false) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
}

else if (mousePressed == false && this.onTarget2 == true) {
this._x -= (this._x-this.myFinalX2)/5;
this._y -= (this._y-this.myFinalY2)/5;
}
};

Now, i can drop the circle on each target, and if i drag it away it will go back to it's starting position. But if i put in, let's say, on targetcircle1, then i won't be able to drag it on targetcircle2. Why? I assume the error to be in the second part of the code...but...what's the problem? Sorry for being such a bad student---

Thanks in advance,
Fede

2008-09-27: Bill Trikojus said:
Hi Fede

this question should probably be posted on a forum as it is difficult to work through more complex issues in this comments area, but I'll have one more guess. I think when you detect that you have dropped on target1, for example, you need to make sure that you set the onTarget2 variable back to false

eg



circle_mc.onRelease = circle_mc.onReleaseOutside=function () {
stopDrag();
if (this._droptarget == "/targetCircle1") {
this.onTarget = true;
this.onTarget2 = false;
_root.targetCircle1.gotoAndStop(2);
}
else if (this._droptarget == "/targetCircle2") {
this.onTarget2 = true;
this.onTarget = false;
_root.targetCircle2.gotoAndStop(2);
} else {
this.onTarget = false;
this.onTarget2 = false;
_root.targetCircle.gotoAndStop(1);
}
};


give that a shot

cheers

--------
iStaySafe - Emergency App for iPhone


2008-09-27: fede said:
Thanks bill, you are a genius!
The problem was: Since there was no chance for onTarget2 to be false, the circle would never switch back to his starting pos after being dragged on target1...

The code, if anyone needs it, is:

circle_mc.onPress = function() {
startDrag(this);
};
circle_mc.onRelease = circle_mc.onReleaseOutside=function () {
stopDrag();
if (this._droptarget == "/targetCircle1") {
this.onTarget = true;
_root.targetCircle1.gotoAndStop(2);
} else if (this._droptarget == "/targetCircle2") {
this.onTarget2 = true;
_root.targetCircle2.gotoAndStop(2);
} else {
this.onTarget = false;
this.onTarget2 = false;
_root.targetCircle.gotoAndStop(1);
}
};
//the variables below will store the clips starting position
circle_mc.myHomeX = circle_mc._x;
circle_mc.myHomeY = circle_mc._y;
//the variables below will store the clips end position
circle_mc.myFinalX = 450;
circle_mc.myFinalY = 250;
circle_mc.myFinalX2 = 110;
circle_mc.myFinalY2 = 286;
circle_mc.onMouseDown = function() {
//this variable tells us if the mouse is up or down
mousePressed = true;
};
circle_mc.onMouseUp = function() {
mousePressed = false;
};
circle_mc.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (mousePressed == false && this.onTarget == false && this.onTarget2 == false) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (mousePressed == false && this.onTarget == true) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
} else if (mousePressed == false && this.onTarget2 == true) {
this._x -= (this._x-this.myFinalX2)/5;
this._y -= (this._y-this.myFinalY2)/5;
}
};


Thanks again Bill!

fede

2008-10-14: Erik said:
Thank you for the great tutorial Bill. I copied your code and I can drag and drop multiple movie clips. My problem is when circle_mc is dropped on targetCircle it doesn’t play frame 2 of the targetCircle movie clip. I’m trying to make it when circle_mc is dropped on targetCircle, targetCircle will play a movie clip. Does this make sense?

2008-10-24: Volker said:
Hello,

im happy to found this page and the drag an drop function (i used the multiple targets function) works pretty well, but:
How do i get this work in AS3?
'Cause i want to implement the code in another Flash-project written in AS3!
Unfortunatly its very important for me to get this work in AS3. Need help please.

Here is my code:
var theClipIWasDroppedOn:String;

function dragSetup(clip, targ1, targ2) {

clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};

clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if ((eval(this._droptarget) == targ1) || (eval(this._droptarget) == targ2)) {
this.onTarget = true;

theClipIWasDroppedOn = eval(this._droptarget);
theClipIWasDroppedOn.gotoAndStop(2);
} else {
this.onTarget = false;
targ1.gotoAndStop(1);
targ2.gotoAndStop(1);
}
};

//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = theClipIWasDroppedOn._x;
clip.myFinalY = theClipIWasDroppedOn._y;

clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x - this.myHomeX)/5;
this._y -= (this._y - this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x-= (this._x - this.myFinalX._x)/5;
this._y-= (this._y - this.myFinalY._y)/5;
}
};
}

dragSetup(circle_mc,targetCircle1,targetCircle2);
dragSetup(circle2_mc,targetCircle1,targetCircle2);
___________________
And thats the Error message in AS3:
TypeError: Error #1009: Der Zugriff auf eine Eigenschaft oder eine Methode eines null-Objektverweises ist nicht möglich.
at drag_n_drop_multiple_fla::MainTimeline/dragSetup()
at drag_n_drop_multiple_fla::MainTimeline/frame1()
_______________________
My starting point was some kind of EventListener, but how do i realize it?

greetings

volker

2008-10-24: Volker said:
hello,

second state:
i rewrote the code to validate in AS3. But there's a problem with the "dropTarget" method.

i have two instances (targetCircle1 and 2) on stage an the two dragable circles. The dropTarget method doesnt correctly handle the instancces underneath the dragable circles... my two instances are recognized from dropTarget as "instance1" and "instance2", not as described above. Additionally the x and y value of thes instances are 0, not the same as the real circle instances... im really confused...

here the new code:
______________
import flash.display.*;
import flash.events.*;

//VARIABLES
var dropZone;
var actObjectClicked:MovieClip;
var myHomeX:Number;
var myHomeY:Number;

initialize();

// EVENT LISTENERS
circle_mc.addEventListener(MouseEvent.MOUSE_DOWN, clipMouseDown);
circle2_mc.addEventListener(MouseEvent.MOUSE_DOWN, clipMouseDown);
circle_mc.addEventListener(MouseEvent.MOUSE_UP, clipMouseUp);
circle2_mc.addEventListener(MouseEvent.MOUSE_UP, clipMouseUp);
circle_mc.buttonMode = true;
circle2_mc.buttonMode = true;

function initialize()
{
//store initial positions
circle_mc.myHomeX = circle_mc.x;
circle_mc.myHomeY = circle_mc.y;
circle2_mc.myHomeX = circle2_mc.x;
circle2_mc.myHomeY = circle2_mc.y;

}

function clipMouseDown(e:MouseEvent):void{
actObjectClicked = MovieClip(e.target);
actObjectClicked.startDrag();
}
function clipMouseUp(e:MouseEvent):void
{
stopDrag();
dropZone = actObjectClicked.dropTarget;
if ((dropZone == targetCircle1) || (dropZone == targetCircle2)) {
trace("Hit");
//dropZone.gotoAndStop(2);

actObjectClicked.x -= (actObjectClicked.x - actObjectClicked.dropTarget.x);
actObjectClicked.y -= (actObjectClicked.y - actObjectClicked.dropTarget.y);

} else {
targetCircle1.gotoAndStop(1);
targetCircle2.gotoAndStop(1);

actObjectClicked.x -= (actObjectClicked.x - actObjectClicked.myHomeX);
actObjectClicked.y -= (actObjectClicked.y - actObjectClicked.myHomeY);
//if the circle is dropped on any part of the target it slides to the center of the target
}
}
______________

greetings

volker


2008-10-24: Bill Trikojus said:
Hi Volker

I've added an as3 version to the downloads at the end of the tute. You might also be interested in checking out this tute

Building a flash game in actionscript 3

cheers
--------
iStaySafe - Emergency App for iPhone


2008-10-24: Volker said:
Hi Bill,

thanks a lot for the hint, i must have been blind... the as3 file solves my problem and also clears the dropTarget issue, i had. (the small but important ".parent" is the solution)

And thanks for the link, think the tute will prove useful...

greetings from germany.

Volker

2008-10-24: Volker said:
i forgot to mention some other requirements / issues:

1. all targets shall be valid targets for both drag-objects.

2. id like to delete the enterframe function, i want to handle the clips-behaviour directly from the stopDragging function inside the if-case.
Or do you have an other idea? (I need to call functions from there)

This is important because i need access to the targets name it was dropped . It doesnt help me to specifiy the final position of the clip only to 1 target. It needs to be dynamically.

greetings

2008-10-27: Bill Trikojus said:
Hi Volker

Time to post this on a forum I think. Check out actionscript.org

cheers
--------
iStaySafe - Emergency App for iPhone


2008-11-08: Claudio Bueno said:
Hi Bill!

Very nice work on this tutorial, really cool.

I'm trying to adjust it to this quiz I'm working on where I can drag one objet and drop to any target and it will tell if it is correct or not.

My knowledge at AS is very poor I tried a couple of things but none worked.

IntAct 302g - Place the continent names...
Example I saw at this url:
http://www.webwasp.co.uk/tutorials/A_IntAct-02-drag-drop/index.php


See below the AS:
function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
this.gotoAndPlay(2);
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
};

//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}

dragSetup(fax,alvo_fax);
dragSetup(sonorizacao,alvo_som);
dragSetup(microfone,alvo_microfone);
dragSetup(notebook,alvo_notebook);
dragSetup(projetor,alvo_projetor);
dragSetup(ar,alvo_ar);
dragSetup(telao,alvo_telao);
dragSetup(caneta,alvo_caneta);


2008-11-08: Bill Trikojus said:
You need to pass an array of targets to the setup function and then loop through that array when the drag item is dropped to see if you are on any of the targets. In each of the targets store a variable such as

alvo_caneta.correctClip=caneta
alvo_telao.correctClip=telao
//etc

so when an item is dropped on a target, you check of the var inside that target is equal to the clip that was dropped, and if it was then the answer was correct

You loop through an array with a for loop

cheers
--------
iStaySafe - Emergency App for iPhone


2008-11-15: JD said:
Fantastic Tutorial Bill. Thank you. It has really been a great help in learning flash interactivity.

Could you tell me how I might be able to have it make duplicates of itself as you drag from the original position?

In other words, when you drag it, there is a dragible duplicate at the origin

I am trying to do it with attachMovie, and (or)duplicateMovie.

function dragSetup(clip, targArray) {
clip.onPress = function() {
startDrag(this);
this.beingDragged = true;
duplicateMovieClip(clip, "clip"+1, 1);
};


2008-11-15: JD said:
Fantastic Tutorial Bill. Thank you. It has really been a great help in learning flash interactivity.

Could you tell me how I might be able to have it make duplicates of itself as you drag from the original position?

In other words, when you drag it, there is a dragible duplicate at the origin

I am trying to do it with attachMovie, and (or)duplicateMovie.

function dragSetup(clip, targArray) {
clip.onPress = function() {
startDrag(this);
this.beingDragged = true;
duplicateMovieClip(clip, "clip"+1, 1);
};


2008-11-23: nikmauro said:
I am trying to drag multiple items to many target but and one item to one specific target and the items with many target need lock the target from other item in the array

function dragSetup(clip, targArray) {
clip.onPress = function() {
startDrag(this);
this.beingDragged = true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged = false;
for (i=0; i targ = targArray[i];
if (eval(this._droptarget) == targ) {
this.myFinalX=targ._x
this.myFinalY=targ._y
this.onTarget = true;
_root.targ.gotoAndStop(2);
break;
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;

clip.myFinalX = 0;
clip.myFinalY = 0;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}
allTargets = new Array(targetCircle1, targetCircle2, targetCircle3);
dragSetup(circle1_mc,allTargets);
dragSetup(circle2_mc,allTargets);
dragSetup(circle3_mc,allTargets);
dragSetup(circle4_mc,targetCircle4);


2008-11-23: Bill Trikojus said:
Sorry nikmauro but I have no idea what you are asking. You might want to post your question on a Flash forum.

cheers
--------
iStaySafe - Emergency App for iPhone


2008-11-23: Bill Trikojus said:
JD - not exactly sure how you want it to function, but the following code will create a copy of the original clip when it is pressed and then call drag setup on the copy. An extra parameter is added to the function to ensure copies are dragged when pressed and originals are copied.

Hope it helps

import mx.transitions.Tween;
import mx.transitions.easing.*;


function dragSetup(clip, targ, original) {
clip.original = original;
clip.onPress = function() {
if (this.original) {
copy = this.duplicateMovieClip('copy'+_root.getNextHighestDepth(), _root.getNextHighestDepth());
dragSetup(copy,targ,false);
copy.onPress();
} else {

startDrag(this);
}

};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
if (eval(this._droptarget) == targ) {
var tx:Tween = new Tween(this, '_x', Elastic.easeOut, this._x, this.myFinalX, 1, true);
var ty:Tween = new Tween(this, '_y', Elastic.easeOut, this._y, this.myFinalY, 1, true);
targ.gotoAndStop(2);
} else {
var tx:Tween = new Tween(this, '_x', Elastic.easeOut, this._x, this.myHomeX, 1, true);
var ty:Tween = new Tween(this, '_y', Elastic.easeOut, this._y, this.myHomeY, 1, true);
targ.gotoAndStop(1);
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;

}

dragSetup(circle_mc,target_mc,true);
--------
iStaySafe - Emergency App for iPhone


2008-11-23: Bill Trikojus said:
In hindsight it would have be easier and cleaner to set up a separate function for setting up the original clip's onPress and just leaving the dragSetup function as it was

Like this



import mx.transitions.Tween;
import mx.transitions.easing.*;


function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
if (eval(this._droptarget) == targ) {
var tx:Tween = new Tween(this, '_x', Elastic.easeOut, this._x, this.myFinalX, 1, true);
var ty:Tween = new Tween(this, '_y', Elastic.easeOut, this._y, this.myFinalY, 1, true);
targ.gotoAndStop(2);
} else {
var tx:Tween = new Tween(this, '_x', Elastic.easeOut, this._x, this.myHomeX, 1, true);
var ty:Tween = new Tween(this, '_y', Elastic.easeOut, this._y, this.myHomeY, 1, true);
targ.gotoAndStop(1);
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;

}


function origSetup(clip, targ) {
clip.onPress = function() {
copy = this.duplicateMovieClip('copy'+_root.getNextHighestDepth(), _root.getNextHighestDepth());
dragSetup(copy,targ);
copy.onPress();
};
}

origSetup(circle_mc,target_mc);
--------
iStaySafe - Emergency App for iPhone


2008-11-24: JD said:
Bill, that's brilliant. Thank very much. I apologize for not being completely specific. I in fact want to do exactly this, but with an array of targets. I have 27 clips, and 23 targets. I am trying to work your array code into this newest version.

If you could throw me a hint, I would be very appreciative.

Also, something else which has me frustrated, is that I can not seem to set a blendMode for the new clip. The images I am using are bitmaps with a white background. The original movieclips are set to "multiply", but when I drag them, I can see the white background.

I tried using:
this.blendMode = 3;

I also tried
copy.blendMode = 3;

But, it didn't seem to have any effect. Here is where I put it.

clip.onPress = function() {
copy = this.duplicateMovieClip('copy'+_root.getNextHighestDepth(), _root.getNextHighestDepth());
this.blendMode = 3;
dragSetup(copy,targ);


Thank you again :)

2008-11-26: RudyC said:
Hey love the AS2 samples provided. I'm looking to use the multi-D&D code and would like to keep track of the successful drops using a hit counter so that I can show a running count of the good matches and when all items are matched to give a congratulation message. I can add and increment the hit counter when there is a match but how do I know when a successful match is removed from the valid target to reduce the hit by one to keep to count current. Or, how do I prevent a drag item from being moved out once on target. I've played with AS3 D&D code samples that do this with event listeners, but I'm looking for a AS2 solution (Flash8) that preferably is adapted to the sample code here.

2008-12-09: DO said:
Bill,
This tutorial has bee a great help! Thank you for your sharing!
I have a question similar to JD's regarding multiple copies to drag. I've used the code you provided to him to make a copy of the clip when you drag it. However when i click to drag another copy the new copy replaces the first copy. How could i change the code so that it will keep creating new copies each time it is dragged without replacing the other copies? Or is there a way to specify that it will make 10 copies but no more? Any help or hints would be greatly appreciated as I am somewhat new to AS. I am using Flash 8 and AS2.
Thank you ahead of time for you help!

2008-12-09: Bill Trikojus said:
On my mobile so I can't view the code but I think you just to make sure the depth param for duplicateMovieClip is always unique. Check out

_root.getNextHighestDepth()
--------
iStaySafe - Emergency App for iPhone


2008-12-09: DO said:
Bill,
Here's the code I am currently using. For the most part it is the code you posted for JD to use. For some reason it isn't dropping on release, I have to click to get it to release. But either way it's still making one copy and then replacing it each time I click on the original. I think I have the depth set right but I'm wondering if it has something to do with an onRelease command in the second function? Any help would be great! Thank you for you expertise!

import mx.transitions.Tween;
import mx.transitions.easing.*;


function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
//I want the dragged item to stay where it's dropped so I left "if" empty
if (eval(this._droptarget) == targ) {
}
else {
var tx:Tween = new Tween(this, '_x', Elastic.easeOut, this._x, this.myHomeX, 1, true);
var ty:Tween = new Tween(this, '_y', Elastic.easeOut, this._y, this.myHomeY, 1, true);
}
};

clip.myHomeX = clip._x;
clip.myHomeY = clip._y;

clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
}

function origSetup(clip, targ) {
clip.onPress = function() {
copy = this.duplicateMovieClip('copy'+_root.getNextHighestDepth, _root.getNextHighestDepth());
dragSetup(copy,targ);
copy.onPress();
};
}

origSetup(test_orn,targetTree);

2008-12-09: Bill Trikojus said:
and this code is on _root?

You are missing () after the first getNextHighestDepth - see if that is the problem.
--------
iStaySafe - Emergency App for iPhone


2008-12-10: DO said:
This code is on _root on the first frame of the top layer. I added the () but still the same thing. It won't drop on release (only on another click) and when i try to drag another one the first one is replaced. I'm just not seeing where the problem lies... Everything seems to be in order...

2008-12-10: Bill Trikojus said:
I just used your exact code and it made a new copy each time so I'm not sure what you're doing wrong there. Regarding the need to click twice to get it to go home initially, add an onMouseUp event

import mx.transitions.Tween;
import mx.transitions.easing.*;


function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
};
clip.onRelease = clip.onReleaseOutside=clip.onMouseUp=function () {
stopDrag();
//I want the dragged item to stay where it's dropped so I left "if" empty
if (eval(this._droptarget) == targ) {
}
else {
var tx:Tween = new Tween(this, '_x', Elastic.easeOut, this._x, this.myHomeX, 1, true);
var ty:Tween = new Tween(this, '_y', Elastic.easeOut, this._y, this.myHomeY, 1, true);
}
};

clip.myHomeX = clip._x;
clip.myHomeY = clip._y;

clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
}

function origSetup(clip, targ) {
clip.onPress = function() {
copy = this.duplicateMovieClip('copy'+_root.getNextHighestDepth(), _root.getNextHighestDepth());
dragSetup(copy,targ);
copy.onPress()


};
}



origSetup(test_orn,targetTree);



cheers
--------
iStaySafe - Emergency App for iPhone


2008-12-10: DO said:
Bill,
You are a life saver! the onMouseUp event was exactly what i needed. I must confess my beginner's lack of knowledge was what got me. I had forgotten that i was publishing to a Flash 6 document. I feel very bad for wasting your time with all that when all I needed was to publish to 7 or later. I sincerely apologize! however I never would have figured this out without your help.
So thank you very much for you expertise and willingness to help! You are greatly appreciated!
Thank you a million times!
Daniel



2008-12-10: Bill Trikojus said:
ah of course. getNextHighestDepth() wasn't added until v7. Anyway, glad you got it sorted.

All the best
Bill
--------
iStaySafe - Emergency App for iPhone


2008-12-11: Nick Court said:
Dear Bill

I have been using your fab script for a while now ... and it has made me also appear fantastic!

However I have encountered a conundrum that I hope you might help me solve.

I have created a couple of swfs with the script as normal ... but I now have to import into Powerpoint for further export via Presenter/Adobe Connect. When viewed in Powerpoint all is well ... but in Connect things drag but do not drop.

Here are examples of the dysfuntional connect version, the working ppt and the script in question.

http://www.le.ac.uk/sc/njc6/connect/index.htm
http://www.le.ac.uk/sc/njc6/connect/dra … roblem.ppt
http://www.le.ac.uk/sc/njc6/connect/draganddrop.txt

Bringing the swf into Connect involves the file being loaded into an unknown level/relationship within the main connect file. So my question is ... is there a way to address the target so that the swf works completely independently of any movie it is loaded into??


2008-12-11: Bill Trikojus said:
Hi Nick,

I'm afraid I don't have any experience displaying flash in powerpoint so I can't help there but regarding your paths, you need to ensure that all paths are 'relative'. If you refer to _root anywhere, the path will break when the movie is loaded into the another movie. All the paths in the tute are relative with the exception of these lines

_root.targ.gotoAndStop(2);

that can just be changed to

targ.gotoAndStop(2);

and it should all work fine.

Hope that helps
--------
iStaySafe - Emergency App for iPhone


2008-12-11: Nick Court said:
Thanks for your reply Bob ... much appreciated ... this must be your lifes work!!

I had got rid of all _root references ..

Hey .. it's only work... I think I can use a cheesier script .. or, of course, encourage people not to use Connect!

Thanks again

Nick

2008-12-14: Kasia said:
Hello Bob, I have problem in quiz file when I want him to be played in another file (.exe projector from fla) I have put this._lockroot=true; to quiz and it helps but I still have problem with drag and drop question

here you find file with this problematic question

http://www.speedyshare.com/601646842.html

when you run it it works ok but when you want him to be played in another swf for example, it doesnt :(

correct positions for letters is: V L W M

2008-12-17: Sandra said:
Hi Bill,

thanks for that great tutorial! I'm completely new to Flash but it (almost) worked out fine. Only problem I have is that my circles don't change color in the multiple version. I copied your code and have no idea why it's not working. I use Flash MX.

Thanks
Sandra

2008-12-17: Bill Trikojus said:
Hi Sandra

Hard to know without seeing some code or the file. If you can upload it somewhere and post a link I'll take a look.

Is everything on _root? You could try getting rid of _root from the code and just say

targ.gotoAndStop(2);

cheers
--------
iStaySafe - Emergency App for iPhone


2008-12-18: Sandra said:
Hi Bill,
thank you for your really fast answer!! When I just looked at my file again I noticed that at some point the second frame within my target mc got lost. Of course it works fine now. I really thought I had checked that before.

Thanks anyway!

2009-01-30: Matt said:
This works great on the root, but I am loading into level500.

I think this needs to be changed,

if (this._droptarget == "/targetCircle") {

Thoughts?

2009-01-30: Bill Trikojus said:
If you trace the droptarget you should be able to get the full path

trace(eval(this._droptarget))

should end up with something like

if (eval(this._droptarget) == _level500.targetCircle) {

cheers
--------
Best Apps for Teens


2009-02-05: Yoma said:
Thank you so much - this is a life saver!!!

2009-02-12: David said:
Thanks for the tutorial Bill. Fantastic.

Im relatively new to flash, and have everything you had in your tutorial working fine. My problem is that once I have ALL the circles on their targets, I want it to give the person feedback, but not until all are in correct position. Do you have something to help with this? Im guessing that i need to tell it to move to frame 3, but am unsure how to do this, and also unsure on how to tell it to wait till all are correct. I havent made any changes from your original code.

Thanks in advance.

2009-02-14: Andy said:
Great tutorial!

I have made a "reset button" as

reset1.onRelease = function () {

circle_mc._x = circle_mc.myHomeX;
circle_mc._y = circle_mc.myHomeY;

}

How can i add a smooth motion to move circle_mc into the start position?

Thanks in advance.



2009-02-28: brendan said:
what an awesome tutorial, and you are so helpful and patient. I think it's amzing how you replied to, and answered all the questions people posted. Your knowledge is very impressive, where can I find more lessons you've created?

2009-03-04: Bill Trikojus said:
Hi Brendan

Just click the Flash link in the menu on the left for many more tutorials.

cheers
--------
Best Apps for Teens


2009-03-06: Adrian said:
Hi Bill !

Excellent tutorial , really .. But i don´t know what part of the code i must to change to create three targets and two dragable MC, where the MCclips has been a correct and incorrect answers (go to and play other scenes when the two MCclips has been drag) and most be dragables on three targets.

Mi code is this but not work ..

function dragSetup(clip, targ, targ1) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ || eval(this._droptarget) == targ1) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
};

clip.myHomeX = clip._x;
clip.myHomeY = clip._y;

clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
clip.onEnterFrame = function() {

if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;

} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}

dragSetup(circle_mc,targetCircle);
dragSetup(circle2_mc,targetCircle2);

Note * The last lines of code i put :
1 .- (circle_mc,targetCircle, targetCircle2, TargetCircle3);

2.- (circle_mc,targetCircle);
(circle_mc,targetCircle2);
(circle_mc,targetCircle3);

and use ...

(circle_mc,targetCircle and targetCircle2);

and ,,

(circle_mc,targetCircle or targetcircle2);

but any of two MC is drag into target 3.

Thank for your help

2009-03-06: Bill Trikojus said:
Hi Adrian

there are too many issues to work through in this forum. You need to post it on a proper Flash forum such as actionscript.org where there are thousands of users and the ability to upload files.

cheers
--------
Best Apps for Teens


2009-03-09: David said:
Thanks for the tutorial Bill. Fantastic.

Im relatively new to flash, and have everything you had in your tutorial working fine. My problem is that once I have ALL the circles on their targets, I want it to give the person feedback, but not until all are in correct position. Do you have something to help with this? Im guessing that i need to tell it to move to frame 3, but am unsure how to do this, and also unsure on how to tell it to wait till all are correct. I havent made any changes from your original code.

Thanks in advance.

2009-03-12: Adrian said:
Hi again Bill ...

I tryed to fix my code but i can´t. I read all the post many times to understand in the correct way.

I have 2 Drag MC and 3 targets ... but still don´t work.
And i want to my 2 MC`s can drag on any of my 3 targets.
But in the movie when i take the MC 1 or 2 to put in the target 1 ,2 or 3 ... The MC´s drop down only in the target 1 , and the targets 2 and 3 will return the MC´s to target 1....
Why ???

This my code ...
i follow your explains.

function dragSetup(clip,targ,targ1,targ2) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ || eval(this._droptarget) == targ1 || eval(this._droptarget) == targ2) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
};

clip.myHomeX = clip._x;
clip.myHomeY = clip._y;

clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
clip.onEnterFrame = function() {


if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;

} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}

dragSetup(circle_mc,targetCircle,targetCircle2,targetCircle3);
dragSetup(circle2_mc,targetCircle,targetCircle2,targetCircle3);

Thnks for your time.


2009-03-12: Bill Trikojus said:
Like I said - this would be better dealt with on a proper forum.

You have hard coded the finalX and Y positions as the first targets x and y - I assume you want the dropped clip to ease to the middle of the target it was actually dropped on? Also when you drop on any target you are telling the first target to go to frame 2 - I doubt this is what you want. Try this


function dragSetup(clip,targ,targ1,targ2) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
theDrop=eval(this._droptarget);
if ( theDrop == targ || theDrop == targ1 || theDrop == targ2) {
this.onTarget = true;
theDrop.gotoAndStop(2);
//ease to middle of clip it was dropped on
this.myFinalX = theDrop._x;
this.myFinalY = theDrop._y;
} else {
this.onTarget = false;
//I'll let you figure out which clips need to be reset
_root.targ.gotoAndStop(1);
}
};

clip.myHomeX = clip._x;
clip.myHomeY = clip._y;


clip.onEnterFrame = function() {


if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;

} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}

dragSetup(circle_mc,targetCircle,targetCircle2,targetCircle3);
dragSetup(circle2_mc,targetCircle,targetCircle2,targetCircle3);


cheers
--------
Best Apps for Teens


2009-03-13: Adrian said:
Wow .... This like i need ... Thank you very much
: D !!!

2009-03-31: Miranda said:
The multiple drag & drop was exactly what I needed! Thx a lot!

2009-04-01: Kev said:
Hi Bill, thanks for the great tutorial! It's been a life saver with this game I'm making. I have just one small problem though, I'm using the multiple target method and can't figure out for the life of me how to get the timeline to go to the next frame for a completion page when all the objects are in their correct place. Any help is much appreciated! Thanks again!

2009-04-03: Richard Watson said:
Hi

I stumbled upon this tutorial. I'm looking for a developer, but the software must run as 3D rather than 2D. You obviously have 2D skills, have you ever dealt with 3D and importing/exporting results.


2009-04-03: Bill Trikojus said:
I'm not currently looking for any freelance work.

thanks anyway
--------
Best Apps for Teens


2009-04-03: Miranda said:
Kev

I also struggled but figuredit out: the code to go to a next frame on completion should go into the code below. I used a counter to see if they had all correct. I also added a notice telling them 'correct' on each good hit.
if (eval(this._droptarget) == eval(("/"+targ))) {
this.onTarget = true;
feedback_txt.setTextFormat(correctFormat);
feedback_txt.htmlText = "Correct!";
myCounter = myCounter+1;

if (myCounter == your number of objects){
gotoAndPlay(2);
}

Hope this makes sense:-)



2009-04-06: David said:
Thank you Miranda.

Exactly what I have been looking for. just had to add:

var myCounter:Number=0

on the top line to get it to work :)

2009-04-22: Bryan said:
The tutorial is great, is there anyway to make it so that both draggable objects can be placed in any of the drop targets? Please let me know, i've been trying but no luck.

2009-05-08: Will said:
Did anybody have any luck getting the movie to play in an Exe file? I have tried all of the _root.lockroot = true; and this.lockroot = true; methods.

Thanks

2009-05-15: Shaun Sleeman said:
Hi Bill,

I saw your tutorial briefly and thought it was brilliant. I am a year 12 student at St Brendan's College, Yeppoon, Queensland, and I am studying Information Technology Systems. For our assignment we are creating flash games using design view and action script 2. But I have a problem. For my assignment I wanted to have drag and drop, But the drag and drop was going to be for the answer. I was wandering if there is anyway I could make it that if the box was dropped in a certain place then the answer is correct?

Thanks,
Shaun

2009-05-15: Bill Trikojus said:
Hi Shaun,

Did you read through all the comments? Pretty sure this question has already been answered.
--------
Best Apps for Teens


2009-05-17: teode said:
Hi Bill, great tutorial!

I have various movie clips that can be dragged around and placed anywhere on the stage.
Now, what i need is to give the user the option of dragging any of these movie clips into a "trash bin" and, as an obvious consequence, the movie clip disappears from stage. Any ideas?
Thanks!

2009-05-17: Jackson McG said:
Hi Bill,

This is a very excellent tutorial I'd like to thank you for making my game easier to create! I am using your script from the drag and drop multiple objects zip:

function dragSetup(clip, targArray) {
clip.onPress = function() {
startDrag(this);
this.beingDragged = true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged = false;
for (i=0; i targ = targArray[i];
if (eval(this._droptarget) == targ) {
this.myFinalX = targ._x;
this.myFinalY = targ._y;
this.onTarget = true;
_root.targ.gotoAndStop(2);
break;
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
clip.myFinalX = 0;
clip.myFinalY = 0;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/2;
this._y -= (this._y-this.myHomeY)/2;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/2;
this._y -= (this._y-this.myFinalY)/2;
}
};
}
allTargets = new Array(s1, s2, s3, s4, s5, s6, s7, s8, s9, s10, s11, s12, s13, s14, s15, s16, s17, s18, s19, s20, s21, s22, s23, s24, s25, s26, s27, s28, s29, s30, s31, s32, s33, s34, s35, s36, s37, s38, s39, s40, s41, s42, s43, s44, s45, s46, s47, s48, s49, s50, s51, s52, s53, s54, s55, s56, s57, s58, s59, s60);
dragSetup(k1, allTargets);
dragSetup(k2, allTargets);
reset.onPress = function() {
k1._x = k1.myHomeX;
k1._y = k1.myHomeY;
k2._x = k2.myHomeX;
k2._y = k2.myHomeY;
};

And it works but I am curious as to how I could make a copy of say K1 when i begin to drag it so that a copy will be in its original place that is also draggable. Thanks!

2009-05-17: Daniel W said:
Hello Bill,

with reference to the 'drag and drop with multiple targets' FLA, I sincerely seek assistance on how to edit its actionscript to accomplish the following:

[B]Scenario[/B]

Flash has a classroom scene - three slides (or draggable objects), a slide projector (droptarget) and a screen on the wall. All three objects share the same droptarget.

A movieclip (info_mc) with four labels (each containing different information for the corresponding slide dragged onto droptarget) - 'reset', 'slide1info', 'slide2info' and 'slide3info' is positioned at the screen area. Default to 'reset' since nothing has been dragged to the droptarget when the swf loads.

If the user drags an slide1 onto the droptarget, the movieclip at the screen area will jump to the corresponding frame label

info_mc.gotoAndStop("slide1info");

But the droptarget can only accomodate one object at a time. When the user drags slide2 over the droptarget where slide1 already resides, slide1 will move back to its original position.

And if the user drags a slide out of the droptarget (i.e. nothing at the droptarget), info_mc will gotoAndStop ("reset").

Any insight will be greatly appreciated.

Rgds,
Dan

2009-05-17: Bill Trikojus said:
teode,

When you detect that the clip has been dropped on the trash, just say

this._visible=false;

cheers
--------
Best Apps for Teens


2009-05-17: Bill Trikojus said:
Jackson,

this question has been answered in the comments above - do a search for "JD"

cheers
--------
Best Apps for Teens


2009-05-17: Bill Trikojus said:
Daniel,

You can get the instance name of the movieclip with this._name . So to get the info_mc to go to the right frame it would be something like

if (eval(this._droptarget) == targ) {
this.onTarget = true;
info_mc.gotoAndStop(this._name+"info");
}


To only allow one item on the target at a time, you could just set the onTarget var to false for all the clips before setting it to true for the one that was dropped


if (eval(this._droptarget) == targ) {
slide1.onTarget=false;
slide2.onTarget=false;
//etc
this.onTarget = true;
info_mc.gotoAndStop(this._name+"info");
}


for the final problem, whenever a clip is dropped and you detect that it wasn't dropped on the target, check if onTarget is true for any of then and if not reset the info clip. So at the moment you might have

//from my original function
} else {
this.onTarget = false;
//check all the clips
//! MEANS FALSE
if(!slide1.onTarget && !slide2.onTarget && !another_mc.onTarget){
info_mc.gotoAndStop("reset");
}
_root.targ.gotoAndStop(1);
}


cheers

--------
Best Apps for Teens


2009-05-18: Daniel W said:
Thank you very much for the assistance, Bill. It's greatly appreciated.

Just one last bit to tweak.

But if slide1 already resides at the droptarget and I want it to return to its original position when I drag slide2 to the droptarget, how do I go about it?

Right now, the script doesn't allow me to drag another clip to the droptarget when it's already occupied. I have to drag out slide1, leave the droptarget empty before I can drag slide2 in.

The current actionscript with your edit:

function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ) {
slide1.onTarget = false;
slide2.onTarget = false;
//etc
this.onTarget = true;
info_mc.gotoAndStop(this._name+"info");

} else {
this.onTarget = false;
//check all the clips
//! MEANS FALSE
if(!slide1.onTarget && !slide2.onTarget){
info_mc.gotoAndStop("reset");
}
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}

dragSetup(slide1,dropzone);
dragSetup(slide2,dropzone);


Please advise.

Rgds,
Dan

2009-05-18: Bill Trikojus said:
When you drag another object on, you set onTarget to salse for all the other clips, so this should send the clip that is already on the target home. This is the bit that should do it

if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
--------
Best Apps for Teens


2009-05-18: Daniel W said:
Thank you for the prompt response, Bill.

I follow the logic on setting onTarget to false for all other clips so only the one that is dragged over the droptarget is 'true' but the bug persists.

If slide1 is already at the droptarget, I can't drag slide2 over it (by virtue slide2.onTarget = false; as long as slide1 is at the droptarget). I have to drag out slide1 then I can drag slide2 into the droptarget.

Any insight is greatly appreciated. Thanks for your time once again.

Rgds,
Dan

2009-05-18: Shaun Sleeman said:
Hi Bill,

Thank you for your help. I will try to incorporate this code into my assignment. I will make sure this site has been referenced. Once again, I thank you for your help and thanks for the help that you are giving lots of people.

Regards,
Shaun

2009-05-18: Bill Trikojus said:
Is it possible that you are dropping slide2 on to slide1? The would cause a different _droptarget to be returned which would cause your bug. Try tracing the _droptarget when you drop an item.
--------
Best Apps for Teens


2009-05-18: Daniel W said:
Hello Bill,

in all honesty, I'm an actionscript newbie hence I'm somewhat lost when you tell me to trace the droptarget. My sincere apologies and many thanks for your patience.

If I want to drag slide2 over to the droptarget while it's already occupied by slide1, then in a way I'm 'dropping slide2 over slide1'.

I just need slide1 to vacate from the droptarget as soon slide2 is dragged onto the droptarget and have slide1 return to its original position.

I seek your kind assistance once again.

Rgds,
Dan

2009-05-18: Daniel W said:
Hello Bill,

I found a solution to the problem! :)

I moved the droptarget layer higher than the layer containing the slides and it works. Not the developer's way of solving the problem but at least it works.

Thanks for your kind assistance and patience.

Have a pleasant week ahead.

Best rgds,
Dan

2009-05-18: Bill Trikojus said:
that's an adequate solution if your drop area is invisible.

Glad you got it sorted.
--------
Best Apps for Teens


2009-05-24: nicky said:
Hi Bill,

great tutorial. perfect for what i'm doing, just need a little help, I have 2 movieclips that have the same target, however if one is dragged to the target then you want to drag the other one (to see a different outcome) i want the first one to return to it's home position when second one is clicked on so they're not both on the target at the same time and can't go on top of each other.

Hope this makes sense. Thanks again.
Nicky

2009-05-24: Sobella said:
Hi Bill,

Just wanted to let you know that in my Flash 8, "_root.targ.gotoAndStop(2);" worked fine in the single click and drag movie but not multiple. However, when I removed the _root from both the 1st and 2nd frames, it worked fine.

Also, I don't know if someone else has asked this before (since I didn't have time to go through all the above posts) and I want to know how to make the movie clips stop moving once they've been dropped on their targets. I'm trying to create a spelling quiz for kids and would like to display a 'congrats' message once all the letters are in their place!

Thanks in advance!

2009-05-24: Bill Trikojus said:
Nicky and Sobella,

I believe both of those questions have already been answered in the comments above

cheers
--------
Best Apps for Teens


2009-05-26: Jesse said:
HI,
I have flash cs4. However,I cant open the drag_n_drop_multiple.fla file, but I can open drag_n_dropMX.fla.....any idea why??

Thanks,
Jesse

2009-05-27: Jesse said:
How can I trace the following:

dragSetup(circle_mc,targetCircle);


2009-05-27: Bill Trikojus said:
what exactly are you trying to output?
--------
Best Apps for Teens


2009-05-29: Jesse said:
I'm trying to change: "targetCircle" on MOUSE_OVER.

Ideally I would like to change its state once the circle_mc is hovered over top of it - so that it shows that you've entered and it is ready to drop off.

I would like to trace when it is hit instead of dropped.

Thanks,
Jesse

2009-05-29: Bill Trikojus said:
ok in AS3 when you start dragging the object, start an ENTER_FRAME event that is running a hitTestObject over and over between the dragged object and the target. When hitTestObject returns true, change the state of the target.

cheers
--------
Best Apps for Teens


2009-05-30: Jesse said:
Hi Bill,
Thanks for the feedback.
I tired this but i only get a 'false' when I start dragging. I can get it to return 'true', but only when it is dropped.

IS this where I should be placing the ENTER_FRAME?

function startDragging(e:MouseEvent):void {

e.target.startDrag();
e.target.beingDragged=true;
trace(targ.hitTestObject(e.target));
Tweener.addTween(e.target.dash_mc, {alpha:0, time:0.4, transition:"linear"});
//Assign highest depth to circle
setChildIndex(e.target, numChildren - 1);
trace("highest");
//Trace Hit test
e.target.addEventListener(MouseEvent.ENTER_FRAME, HitTarg);

function HitTarg(event:MouseEvent):void {
trace(e.target.hitTestObject(targ));
}
}

Thanks again,
Jesse

2009-05-30: Bill Trikojus said:
ENTER_FRAME is not a MouseEvent

you want Event.ENTER_FRAME

cheers
--------
Best Apps for Teens


2009-06-01: Jesse said:
Awesome, thanks for the help.
Jesse

2009-06-07: Brian said:
Great Tut. Just wondering I have made a reset button as
reset1.onRelease = function () {

slope_mc._x = slope_mc.myHomeX;
slope_mc._y = slope_mc.myHomeY;

}
when button is pressed it goes to original position but then flys back to target. How can I stop this?

2009-06-07: Bill Trikojus said:
sounds like you also need to set onTarget back to false

reset1.onRelease = function () {
slope.onTarget=false;
slope_mc._x = slope_mc.myHomeX;
slope_mc._y = slope_mc.myHomeY;

}
--------
Best Apps for Teens


2009-06-07: Brian said:
I tried this Bill but no go.Would it make difference how many variables there are?

2009-06-07: Brian said:
Sorry Bill, can see now should be slope_mc.onTarget= false; Thanks for that. I think I might watch the easing tut to see how to ease them back to original position.

2009-06-15: Darren said:
Hi Bill.

I'm creating a website that use the letters of the alphabet that can be dragged onto different targets in order to spell out the user's name. I stumbled across your code and I have now managed to achieve what I wanted. My question is to do with duplicating the letters in case more than one of the same kind is required.

The code that I used of yours (and slightly modified) is as follows:

function dragSetup(clip, targArray) {
clip.onPress = function() {
startDrag(this);
this._x -= this._width/5;
this._y -= this._height/5;
this._xscale = 375;
this._yscale = 375;
this.beingDragged = true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged = false;
for (i=0; i targ = targArray[i];
if (eval(this._droptarget) == targ) {
this.myFinalX = targ._x;
this.myFinalY = targ._y;
this.onTarget = true;
this._xscale = 375;
this._yscale = 375;
_root.targ.gotoAndPlay(2);
break;
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
this._xscale = 100;
this._yscale = 100;
}
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;

clip.myFinalX = 0;
clip.myFinalY = 0;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}
allTargets = new Array(circle1, circle2, circle3, circle4, circle5, circle6, circle7, circle8);
dragSetup(letterA,allTargets);
dragSetup(letterB,allTargets);
dragSetup(letterC,allTargets);
dragSetup(letterD,allTargets);
dragSetup(letterE,allTargets);
dragSetup(letterF,allTargets);
dragSetup(letterG,allTargets);
dragSetup(letterH,allTargets);
dragSetup(letterI,allTargets);
dragSetup(letterJ,allTargets);
dragSetup(letterK,allTargets);
dragSetup(letterL,allTargets);
dragSetup(letterM,allTargets);
dragSetup(letterN,allTargets);
dragSetup(letterO,allTargets);
dragSetup(letterP,allTargets);
dragSetup(letterQ,allTargets);
dragSetup(letterR,allTargets);
dragSetup(letterS,allTargets);
dragSetup(letterT,allTargets);
dragSetup(letterU,allTargets);
dragSetup(letterV,allTargets);
dragSetup(letterW,allTargets);
dragSetup(letterX,allTargets);
dragSetup(letterY,allTargets);
dragSetup(letterZ,allTargets);
dragSetup(letterAmpersand,allTargets);

Is there any code to duplicate the movieclips that can be inserted into the above actionscript?

I would really appriciate and help that you may be able to offer me.

2009-06-15: Bill Trikojus said:
Hi Darren,

I have already answered that one for JD up above.

cheers
--------
Best Apps for Teens


2009-06-15: Darren said:
Hi Bill

Thanks for that and the quick response. I tried pasting the code that you gave to JD and it worked fine but it won't go to the targets as it did before.

Do you know why? Many thanks.

2009-06-16: Jon said:
Hi Bill

I'm hoping to add a reveal button and a reset button that would reset everything but also randomise the start position of the drags (i Have six drags). Could you advise on this?

Thanks in advance :-)
JJ

2009-06-17: Stan said:
hi, i was wondering how i would make it so that when the circle gets to the target it can no longer be dragged out again

2009-06-18: Bill Trikojus said:
Stan - turn events off by setting them to null

eg

this.onPress=null;

JJ - I don't know what you want to reset but the random position is easy

function reset(){
drag1_mc._x=Math.random()*Stage.width;
drag1_mc._y=Math.random()*Stage.height;
//other stuff


}


cheers

--------
Best Apps for Teens


2009-06-24: Darren said:
Hi Bill

Further to my earlier posting, other that my movieclips of the letters not snapping to the targets, if the movieclips are returned to their original position you can't then move them again. They just go back to the start position. Any ideas?

2009-07-28: Jesse said:
Hi Bill,
I'm tracing when the circle hits the target.
This works great. However, I was wondering if I could trace the circle over multiple targets/targ instead of just the correct target?
Heres my code so far:
trace(e.target.hitTestObject(targ));
{
if (e.target.hitTestObject(targ)) {
trace("Hit it");

} else { trace("Not yet");
}

Thanks,
Jesse

2009-07-28: Jesse said:
To answer my previous question about using hitTestObject on more then one object:

trace((e.target.hitTestObject(target1))||((e.target.hitTestObject(target2))));
{
if ((e.target.hitTestObject(target1))||((e.target.hitTestObject(target2)))) {
trace("Hit it");
} else {
trace("Not yet");
}
};

2009-07-29: Brian Landrigan said:
Bill, I was wondering if it is possible to have multiple objects but with only two targets. So some of the objects will have the same target but not go over the top of each other in the centre. Is this possible?

2009-07-30: Bill Trikojus said:
Pretty sure the multiple target stuff is all covered in the comments above. Not sure what you mean about going over the top of each other - one clip will always be above another clip - you can only have one clip at each depth. To bring the dragged clip to the front use something like

this.swapDepths(_root.getNextHighestDepth());

cheers
--------
Best Apps for Teens


2009-07-30: Brian Landrigan said:
What I mean is: the target is set so that the object being dragged moves to the centre of the target. If there is more than one object per target they will overlap each other. Can you make them just stop in the target and not move to the centre?

2009-07-30: Bill Trikojus said:
These lines move the clip to the center of the target

this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;

just remove those 2 lines.

cheers
--------
Best Apps for Teens


2009-08-20: arjang said:
hey there. great pice of code you have provided man, please know at least I aprreciate you sharing this for free ALOT!!!!!

I have question also: I would like to limit the area, within the to be dragged object can be moved around and no further. is that possible?

thanx!

2009-08-20: Bill Trikojus said:
Sure, that's easy. Just check the startDrag entry in the manual. There are some extra parameters you can provide when calling that method that will limit the area in which the object can be dragged.

cheers
--------
Best Apps for Teens


2009-08-20: arjang said:
hey thanx for the quick response.I'll have a look at it.

Right now I have a different more obvious problem, I'd appreciate a hint towards the right direction:

I have managed to have 3 different objects be draggable into a certain droparea. This is my ite's menu. SO each time a certain object is dropped inside a certain page will be shown, via loadMovie. The command for that is placed,depending which menu selected, on the 2nd,3rd,4th frame etc. Each menu will load a swf into my flash movie. each being a viewer within a folder.

the PROBLEM is: there seems always one movie/viewer being loaded. It shows for alol of them the same pictures. I had a look at the options.as . I changed the links to the xml file and the images folder. still the same problem.



I also tried to put each viewer in it's very own moviel placeholder. Also tired unloading the last movie. None has worked.

My guess is the xml file is loaded differently then say a swf file so unloading the movie wont help and the loaded xml file then applys on all to be loaded viewers.

I say that because I noticed it doesn't matter which menu item you select first...thats the one which will be displayed from then on for all viewers.

I'm an absolute beginner. so please do explain it to me a litle more detailed then you usually would. this is my first flash website I'm making. And I don't know programming. But I'm quick to pick up anything. just give it a go :).

thanks

ps. is there a possibility to place a donation for you here (no money!!!!)?

2009-08-21: Bill Trikojus said:
no way to donate money, but thank you for the offer.

I'm not sure I really understand your problem, and it is probably one that would be easier to work through on a flash forum such as actionscript.org, but I think part of the problem might be the fact that you are jumping frames when an object is dragged on. Try leaving everything on frame one and just passing the loadMovie call a different swf name when a new item is dropped on the target. If that doesn't work, please post it on a flash forum where you will be able to post code, attach files etc.

cheers
--------
Best Apps for Teens


2009-08-25: Andrew said:
Hi Bill,

I have a game where i want to be able to drag multiple objects onto a single target but each object will have a different end position within the target.

Is there a way to do this without having to duplicate the code over and over again for each object?

2009-08-25: Bill Trikojus said:
probably the easiest way is to add an extra parameter to the function that takes a pixel number. This would store the distance from the center of the target to set as the final x and y for the clicp being dragged

eg

function dragSetup(clip, targ,offsetX,offsetY) {


and then

//the variables below will store the clips end position
clip.myFinalX = targ._x+offsetX;
clip.myFinalY = targ._y+offsetY;



then when you call the function say something like

dragSetup(drag1, targ1,50,0)
dragSetup(drag2, targ1,50,-50)


cheers

--------
Best Apps for Teens


2009-08-25: Andrew said:
Thanks Bill, that works perfect. Much appreciated.

2009-09-25: renato said:
Hi Bill,

Thanks for the great tutorial. I've searched through all the comments but can't find a solution to my problem. I've created a game where the user drags clothes onto a model, each item of clothing has a different price associated to it. I have a "total" variable that adds it all up. Problem is when multiple items are on top of each other the "total" var doesn't always register the amount. This is the code I have on the items:

on (release) {
if (_root.jacket1._droptarget == "/targetJ") {
_root.j1 = 179.99;
}
if (_root.jacket1._droptarget != "/targetJ") {
_root.j1 = 0;
}
_root.total = _root.j1 + _root.j2 + _root.j3;
}

Thanks in advance,
Renato

2009-09-25: renato said:
Hi Bill,

Think ! solved it, I used hitTest on the items and it seems to work.

onClipEvent (enterFrame) {
if (_root.jacket1, hitTest(_root.targetJ)) {
_root.j1 = 179.99;
} else {
_root.j1 = 0;
}



2009-10-26: Matt said:
Hi there,
This tutorial is really great its helped me understand alot:)
I am trying to adapt it for my own needs but cant quite get it right. I need to adapt your multiple drag and drop movie so that i have six drag and drop colours with three different targets. I need the frames in the target clips to be from 1-6, 1 for each of the draggable colours so that the gotoandstop goes to the targetframe assigned to each colour. I hope this makes sense.

Many Thanks

Matt

2009-11-15: Fred B. said:
Hi Bill,
First thank's for this tuto, i haved leanr many things ...
I haved try to do something diferent. I want try to have one target with many clip. That's ok...but i try to find solution to reset position of one clip when i drop a another one to target... with a hit test maybe ? or maybe with a test on the onPress ? am i in the good direction ? am i clear with my questions ? sorry for my bad english....


function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
clip.myHomeW = clip._width;
clip.myHomeH = clip._height;
//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
clip.myFinalW = targ._width;
clip.myFinalH = targ._height;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
this._width -= (this._width-this.myHomeW)/5;
this._height -= (this._height-this.myHomeH)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
this._width -= (this._width-this.myFinalW)/5;
this._height -= (this._height-this.myFinalH)/5;
}

};
}

dragSetup(vid_mc,target_frame);
dragSetup(vid2_mc,target_frame);

by advance thank's for your answer.

Fred

2009-11-18: Gala said:
Hi Bill,
The tutorial is really helpful for beginners like me.I appreciate your work a lot.
Unfortunately, I can't get it work. I have been looking at the code for two days already. I can't find the error. I can drag my MC but can not drop to the target.
Here is the code:
function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
};

clip.myHomeX = clip._x;
clip.myHomeY = clip._y;

clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
clip.onEnterFrame = function() {
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;

} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}

dragSetup(internet,containerInternet);
dragSetup(server,containerServer);

2009-11-18: walchi said:
hi im looking for a way to duplicate movie clips in the back once the old movieclips are in they target areas

10x

2009-11-19: gala said:
Resolved

2009-12-02: sam said:
Wow! This is a huge post! I am dragging a slider along a timeline (like in flash - the playhead) and when it gets to the edge I want the timeline contents (like keyframes in flash) to start dragging.

How do you suggest I do this? I am using a hittest collision (as2) and its moving but not qute right..

2009-12-16: gala said:
Bill,
Thank you again or this tutorial. It is amazing!
I just stuck with validation.For some reasons I can not get numAttempts or correctAnsw numbers. Please, please help!

function dragSetup(clip, targArray)
{
var numAttempts:Number = 0;
var correctAnsw:Number = 0;
clip.onPress = function()
{
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {

stopDrag();
this.beingDragged=false;
for (i=0; i targ = targArray[i];
if (eval(this._droptarget) == targ)
{
this.myFinalX=targ._x
this.myFinalY=targ._y
this.onTarget = true;
message_txt.text = "Correct";
correctAnsw++;
break;
}
else if (eval(this._droptarget) != targ && numAttempts<3)
{ this.onTarget = false;
message_txt.text = "Incorrect";
numAttempts++;

}

else if (eval(this._droptarget) != targ && numAttempts >3)
{
message_txt.text = "Too many failed attempts! Please try again";
numAttempts=0;
}
} //for ends
};//onRelease ends

if (correctAnsw == 12)
{
_level1.gotoAndPlay(2);
}


//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;


//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;


clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;

//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};//onEnter function ends

}

stop();

2009-12-17: Bill Trikojus said:
it looks like this

if (correctAnsw == 12)
{
_level1.gotoAndPlay(2);
}

is sitting outside the onRelease function. It needs to go inside it so it is run each time on object is dropped.

hope that helps
--------
App to track my kids


2009-12-17: Bill Trikojus said:
Walchi - see my reply to JD above.

cheers
--------
App to track my kids


2009-12-18: gala said:
Thank you very much for the prompt response!
Unfortunately, it doesn't work.
I also try figure out how to count all failed attempts, for all mc , not
only for this.beingDragged.
In addition, after 3 failed attempts I want send all mc home.

I would greatly appreciate any advise. I have been fighting this problem for a week already and I'm on the verge of tears.


function dragSetup(clip, targArray)
{
var numAttempts:Number=0;
var correctAnsw:Number=0 ;
clip.onPress = function()
{
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {

stopDrag();
this.beingDragged=false;
for (i=0; i targ = targArray[i];
if (eval(this._droptarget) == targ)
{
this.myFinalX=targ._x
this.myFinalY=targ._y
this.onTarget = true;
message_txt.text = "Correct";
correctAnsw++;
break;
}
else
{
message_txt.text = "Incorrect";
numAttempts++ ;
}

if( numAttempts > 3 )
{
message_txt.text = "Too many failed attempts! Please try again";
}

if (correctAnsw == 12)
{
message_txt.text = "You Won";
}
} //for ends
};// onRellease ends



//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;


//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;


clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};//onEnter function ends

}

stop();

2009-12-22: greg said:
Hi Bill,
Thanks for the great tutorial!
Just one question:
if I have an array of targets and an array of clips should I create a nested "for" statement?

I would appreciate your comments.


2009-12-23: Bill Trikojus said:
make the second parameter for the function the array of targets (assuming each dragable object can be dragged to any target), put a for loop in the onrelease to loop through the target array. Then make an array of dragable objects and loop through that to set them all up

something like


dragableObjects=new Array(drag1,drag2);
targetObjects=new Array(targ1,targ2,targ3);

function dragSetup(clip, targArray) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
for(i=0;i targ=targetObjects[i];
if (eval(this._droptarget) == targ) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}


for(i=0;i dragSetup(dragableObjects[i],targetObjects);
}






cheers




--------
App to track my kids


2009-12-23: Bill Trikojus said:
for loops broken in above code but you should be able to figure it out.
--------
App to track my kids


2009-12-24: gala said:
Hello Bill,
Happy Holidays!

Thank you for your comments. I really appreciate it!
You comments helped me a lot.
However , I'm still fighting the problem.
I don't understand how get the correct "numAttempts" value.
It seams easy , but I can't get it. Counting works for the single clips but with the array of clips "Too many failed attempts.." message
appears after fist or second failed attempts.
I have single arrays and single targets as well as array of clips with the arrays of targets
For example:
3 dogs and 3 kennels,
1 fish and 1 fishbowl
2 bird and 2 nests
All dogs and all kennels would be the same, etc

Could you please advise.
Thank you!
clip.onRelease = clip.onReleaseOutside=function () {

stopDrag();
this.beingDragged=false;
for (i=0; i targ = targArray[i];
if (eval(this._droptarget) == targ)
{
this.myFinalX=targ._x
this.myFinalY=targ._y
this.onTarget = true;
message_txt.text = "Correct";
myCounter++;
if (myCounter == 12)
{
message_txt.text = " You Won";
}
break;

}
else
{ this.onTarget = false;
message_txt.text = "Incorrect";
numAttempts++ ;

if (numAttempts>3 )
{
message_txt.text = "Too many failed attempts! Please try again";
}// if >3 ends
}//else ends
} //for ends
};// onRellease ends

2009-12-25: Bill Trikojus said:
hard to say without seeing the complete code but I can see a couple of problems with the logic. yours is more complicated than mine, so you will need multiple arrays of correct targets (one for kennels, one for nests etc) and this array would be passed as the second parameter to the function and then stored as a variable inside each dragable clip

eg

function dragSetup(clip, targArray) {

//new
clip.myTargetsArray=targArray;

//on press stuff


clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
//for loop to loop through this.myTargetsArray

targ=myTargetsArray[i];
if (eval(this._droptarget) == targ) {
//and the rest
};
}



There is also a problem with the way you are counting 'mistakes'. If I have three correct targets in an array I can obviously only drop on one of them, so counting the other 2 as mistakes seems a little harsh doesn't it?

A better solution would be something like this


//inside the onRelease set a var
this.gotRight=false;

//loop through the correct targets array
//if you find a match with the droptarget say
this.gotRight=true;

//close the for loop then check var - if it is still false you can assume they got it wrong

if(!this.gotRight){
numAttempts++;
//etc
}




Merry Christmas.

--------
App to track my kids


2009-12-28: gala said:
Bill, Thank you very much !!
I got the correct number of failed attempts!!

But now I can't get the target. My clips stick to any empty areas but the correct targets.
Here is the code.

function dragSetup(clip, targArray)
{ numAttempts=0;
myCounter=0 ;
clip.myTargetsArray=targArray;

clip.onPress = function()
{
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {

stopDrag();
this.gotRight=false;
this.beingDragged=false;
for (i=0; i targ = myTargetsArray[i];
if (eval(this._droptarget) == targ)
{

this.myFinalX=targ._x
this.myFinalY=targ._y
this.onTarget = true;
this.gotRight=true;

message_txt.text = "Correct";
myCounter++;
if (myCounter == 6)
{
gotoAndPlay(2);
}
break;

}
else
{
message_txt.text = "Try Again";
}

}
if(!this.gotRight){
numAttempts++;
if(numAttempts >3)
{

bird1_mc.onTarget=false;
bird1_mc._x = bird1_mc.myHomeX;
bird1_mc._y = bird1_mc.myHomeY;

bird2_mc.onTarget=false;
bird2_mc._x = bird2_mc.myHomeX;
bird2_mc._y = bird2_mc.myHomeY;

bird3_mc.onTarget=false;
bird3_mc._x = bird3_mc.myHomeX;
bird3_mc._y = bird3_mc.myHomeY;


dog1_mc.onTarget=false;
dog1_mc._x = dog1_mc.myHomeX;
dog1_mc._y = dog1_mc.myHomeY;

dog2_mc.onTarget=false;
dog2_mc._x = dog2_mc.myHomeX;
dog2_mc._y = dog2_mc.myHomeY;


fish_mc.onTarget=false;
fish_mc._x = fish_mc.myHomeX;
fish_mc._y = fish_mc.myHomeY;

numAttempts=0;
message_txt.text = "Too many failed attempts";
}
}
};



//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;


//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;


clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget ) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget ) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};//onEnter function ends
}
allNests = new Array(nest1_mc, nest2_mc, nest3_mc);
dragSetup(bird1_mc,allNests);
dragSetup(bird2_mc,allNests);
dragSetup(bird3_mc,allNests);


allBirds = new Array(bird1_mc, bird2_mc, bird3_mc);
dragSetup(allBirds,nest1_mc);
dragSetup(allBirds,nest2_mc);
dragSetup(allBirds,nest3_mc);


allKennels = new Array(kennels1_mc, kennels2_mc);
dragSetup(dog1_mc,allKennels);
dragSetup(dog2_mc,allKennels);


allDogs = new Array(dog1_mc, dog2_mc);
dragSetup(allDogs,kennels1_mc);
dragSetup(allDogs,kennels2_mc);


fish = new Array(fishbowl_mc);
dragSetup(fish,fishbowl_mc);
stop();

I'm very sorry for being so annoying but I just don't know where to find info
about it.

2009-12-28: gala said:
I found my mistake. Everything is working now.

Thanks

2009-12-29: Bill Trikojus said:
Good to hear. I would imagine it had something to do with calling the function with the parameters in the wrong order, but please post your solution here for others.

Cheers
--------
App to track my kids


2009-12-29: gala said:
Here it is:
function dragSetup(clip, targArray)
{ numAttempts=0;
myCounter=0 ;
clip.myTargetsArray=targArray;
clip.onPress = function()
{
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {

stopDrag();
this.gotRight=false;
this.beingDragged=false;
for (i=0; i targ = this.myTargetsArray[i];
if (eval(this._droptarget) == targ)
{

this.myFinalX=targ._x
this.myFinalY=targ._y
this.onTarget = true;
this.gotRight=true;
message_txt.text = "Correct";

break;
}
else
{
message_txt.text = "Incorrect";
}

}
if(this.gotRight){
myCounter++;
if (myCounter == 6)
{
gotoAndPlay(2);
}
}
if(!this.gotRight){
numAttempts++;
if(numAttempts >3)
{
message_txt.text = "Too many failed attempts. Please try again";
//everything goes back home here numAttempts=0;

}
}
};



Bill, Thank you very much!!
I learned a lot!

2010-02-01: Nirbhay said:
Very helpful tutorial. Thanks.

2010-02-03: gala said:
Hello Bill,
Could you please direct me on how to add sounds to this game.
Do I need to add one more variable and than go through the array?

function dragSetup(clip, targArray)
{
var soundIncorrect:Sound = new Sound();
soundIncorrect.attachSound("incorrect");

var soundCorrect:Sound = new Sound();
soundCorrect.attachSound("correct1");

var soundAllback:Sound = new Sound();
soundAllback.attachSound("allback");


numAttempts=0;
myCounter=0 ;
clip.myTargetsArray=targArray;
clip.onPress = function()
{
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {

stopDrag();
this.gotRight=false;
this.beingDragged=false;


for (i=0; i targ = this.myTargetsArray[i];
if (eval(this._droptarget) == targ)
{
this.myFinalX=targ._x
this.myFinalY=targ._y
this.onTarget = true;
this.gotRight=true;
soundCorrect.start(0,0);
message_txt.text = "Correct";

break;
}

else
{
message_txt.text = "Incorrect";
soundIncorrect.start();
}//else ends

} //for ends
if(this.gotRight){
myCounter++;
if (myCounter == 12)
{
gotoAndPlay(2);
}
}
if(!this.gotRight){
numAttempts++;


I would really appreciate your advise.
Thank you

2010-02-03: Bill Trikojus said:
create the sound objects and attach the sounds outside the dragSetup function. Then just trigger them when appropriate:

soundAllback.start();

see the sounds tutes for more details - you mentioned one wasn't working for you but they work for pretty much everyone else so try a different browser, update flash plugin etc.

cheers
--------
App to track my kids


2010-02-04: gala said:
Yes, Thank you. I fixed it already.

2010-02-04: Bill Trikojus said:
OK then please post that on here (and the fix for others) so I don't need to bother replying.
--------
App to track my kids


2010-02-19: Annabel Stewart said:
Hi,

I'm trying to create a charm bracelet designer. After spend many nights looking for code to help me, I found yours and it is amazing.

I have one question, I have specified the one area which I want the charm to target, is there any way of having multiple targets for one charm. In other words more positions on the bracelet?

Thanks for sharing this amazing code.



2010-02-20: gala said:
Hi Annabel,
You need to create an array of targets. Something like this
allTargets = new Array(target1_mc, target2_mc, target3_mc);

dragSetup(charm_mc,allTargets);


2010-03-01: mayu said:
Hi bill, im a complete novice at flash, and found your tutorial VERY helpful. my issue is probably easy to solve, but for the lfe of me, i cant figure it out:

where the code states _root.targetCircle.gotoAndStop(2), how do i change this to switch to a different scene rather than different frame with the movie clip, ie. gotoAndPlay("SceneTwo", "FrameOne") - for some reason, this doesnt work.

thanks in advance
mayu

2010-03-01: Bill Trikojus said:
Hi Mayu,

You will need to check the manual for gotoAndPlay but I'm pretty sure the second parameter needs to be a frame number or a frame label, and the first parameter should be the exact name of your scene

eg

gotoAndPlay("SceneTwo", "start")

gotoAndPlay("SceneTwo", 1)

cheers
--------
App to track my kids


2010-03-01: mayu said:
Hi Bill, thanks for your quick reply!

The second paramenter "FrameOne" is a frame label, yet nothing seems to happen when the circle_mc is dropped onto the targetCircle. Perhaps there is another way around this?

I was thinking maybe actionscripting frame 2 in targetCircle with the gotoAndPlay function, however, this too doesnt seem to work.

Thanks again
mayu

2010-03-01: Bill Trikojus said:
Is your scene name correct? By default I think it would be Scene 2

You actually shouldn't use scenes. Just lay out your frame labels on the main timeline of Scene 1.

Anyway if you can't get it working it might help to start a fresh file and just make a basic button and frame label to get your head around gotoAndPlay() without worrying about the drag and drop stuff.

cheers

--------
App to track my kids


2010-03-01: Annabel Stewart said:
Thanks,

I'm struggling to create an array of targets. The targets need to have x and y co ordinates so that the charm sits on the braclet at corresponding links.

Thank again

Annabel

2010-03-01: Annabel Stewart said:
I thought that I would show the code which I have modified, so that the charm finishes on a specified x/y co-ordinate. Is there a way of having multiple x/y co-ordiantes.

function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = 166;
clip.myFinalY = 267;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}


dragSetup(charm1_mc,bracelet1_mc);

2010-03-01: Bill Trikojus said:
There is code above that does exactly what you need - please read through the comments around when nikmauro was posting.
--------
App to track my kids


2010-03-09: Bonnie said:
Im making a simple drag and drop game that has 4 targets numbered 1-4 and the corresponding objects. I used the code you gave and they move around and all but I cant get them to snap to the centre, and also they dont move back to their original position when placed in in the wrong area.

here's the code:

function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}


dragSetup(b1_mc,targetbug1_mc);
dragSetup(b2_mc,targetbug2_mc);
dragSetup(b3_mc,targetbug3_mc);
dragSetup(b4_mc,targetbug4_mc);



2010-03-18: dror said:
hey Bill,
I'm trying to duplicate the icon dragged by using "duplicateMovieClip" but it will only duplicate when i hit the icon again on the target zone and not by itself
also I'm trying to open a editing window for the icons on the hit zone, any suggestions

thanks

function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);

this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = targ;
clip.myFinalY = targ;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {

this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
i=i+1;
duplicateMovieClip(this,'clip'+'i',i);
}
};
}
dragSetup(circle_mc,targetCircle);
dragSetup(circle2_mc,targetCircle);
var i:Number=0;


2010-03-26: Sipazzo said:
I just wanted to thank you so much for the great tutorial and answering everyone's questions. My Flash Professor has checked out for the semester and if it wasn't for finding your tutorial online I would be in a world of hurt. I have still spent an incredible amount of time trying to figure out why mine wouldn't work but after many trips to your site and reading all the Q&As posted, I am happy to say I got it working. Thanks again!

2010-03-26: Bill Trikojus said:
good to hear! Spending hours working through issues is the best way to actually learn something - you should beg your professor to take next semester off as well.

cheers
Bill
--------
App to track my kids


2010-05-12: Nick Coupland said:
Hi Bill,
Firstly i want to say that this is a great tutorial and it has taught me alot. I am currently using your multiple targets script with a few modifications but i would like to add a reset button to move all clips back to there starting position. I have tried a few things with no success. Do you have any idea what would be the best way to do this.
Thanks
Nick

2010-05-12: Bill Trikojus said:
shouldn't be difficult. Do all your dragable clips have the myHomeX and myHomeY vars inside them? If so, your reset button just needs to get those values

reset_mc.onRelease=function(){
clip1._x=clip1.myHomeX;
//etc
}
Bill
iStaySafe - Emergency App for iPhone
--------
App to track my kids


2010-05-13: Nick Coupland said:
Thanks for the reply Bill.
I did what you said and it makes perfect sense but for some reason its not working for me. instead of reseting the objects just jump back to there starting positions and automatically move back to there target areas. I hope that makes sense. Any thoughts?
Thanks
Nick

2010-05-13: Bill Trikojus said:
sounds like you need to set the onTarget var back to false for each one

reset_mc.onRelease=function(){
clip1.onTarget=false;
clip1._x=clip1.myHomeX;
//etc
}
Bill
iStaySafe - Emergency App for iPhone
--------
App to track my kids


2010-05-13: Nick Coupland said:
Thanks Bill,
That worked perfectly, sorry for bothering you for such a simple fix.
Thank you again,
Nick

2010-05-13: Dharshan Venkadesan said:
Thank you..im now creating a new dress up game for Ezzal.com and this code really helped me..

this dragging method is very smooth and easy to modify.

Regards,
Dharshan.
http://www.ezzal.com

2010-05-14: Richard said:
I have 6 objects and 6 targets. Users are required to drag objects to the correct target. If the correct target is hit an affirmative response is given by a separate movie clip. Dropping on an incorrect target gives a negative response.

Can anyone help extend the AS2 above to include these actions?

Here is my incomplete and partially functioning code:

function DragSetup(Obj, Target) {
Obj.Target = Target;
Obj.onPress = function() {
this.x = this._x;
this.y = this._y;
this.startDrag();
};
Obj.onRelease = function() {
this.stopDrag();
Drop = eval(this._droptarget);
for (a in Target) {
if (Drop == Target[a]) {
this._x = Target[a]._x;
this._y = Target[a]._y;
Check = 1;
return;
}
if (!Check) {
this._x = this.x;
this._y = this.y;
}
Check = 0;
}
};
}
DragSetup(tile_mc1, [target_mc1, target_mc2, target_mc3, target_mc4, target_mc5, target_mc6]);
tile_mc1.onPress = function() {
startDrag(this);
};
tile_mc1.onRelease = tile_mc1.onReleaseOutside=function () {
stopDrag();
if (this._droptarget == "/target_mc1, target_mc2, target_mc3") {
this.onTarget = true;
_root.character_mc.gotoAndStop("smile");
} else {
this.onTarget = false;
_root.character_mc.gotoAndStop("frown");
}
};
DragSetup(tile_mc2, [target_mc1, target_mc2, target_mc3, target_mc4, target_mc5, target_mc6]);
DragSetup(tile_mc3, [target_mc1, target_mc2, target_mc3, target_mc4, target_mc5, target_mc6]);
DragSetup(tile_mc4, [target_mc1, target_mc2, target_mc3, target_mc4, target_mc5, target_mc6]);
tile_mc4.onPress = function() {
startDrag(this);
};
tile_mc4.onRelease = tile_mc4.onReleaseOutside=function () {
stopDrag();
if (this._droptarget == "/target_mc4, target_mc5, target_mc6") {
this.onTarget = true;
_root.character_mc.gotoAndStop("smile");
} else {
this.onTarget = false;
_root.character_mc.gotoAndStop("frown");
}
};
DragSetup(tile_mc5, [target_mc1, target_mc2, target_mc3, target_mc4, target_mc5, target_mc6]);
DragSetup(tile_mc6, [target_mc1, target_mc2, target_mc3, target_mc4, target_mc5, target_mc6]);

Super grateful. Rich

2010-05-14: Bill Trikojus said:
Hi Richard,

Have you skimmed over the comments above? Pretty sure that has already been covered. Your if statement would look more like this

if (this._droptarget == "/target_mc4" || this._droptarget == "/target_mc5" || this._droptarget == "/target_mc6") {
Bill
iStaySafe - Emergency App for iPhone
--------
App to track my kids


2010-05-18: Kayleigh said:
Hi, I tryed using your code for my flash presentation but completly confused myself.
What I am trying to do is a drag and drop quiz where there are three answers (salt, mascara and toothpaste) and they will be dragged to the 'drag answer here' space on the slide. I want the correct answer (salt) to lead to a page where it tells the user they got the answer correct, and for the other two answers to take the user to the pages where it tells them they got it wrong.
So all three answers are dragged to the same area but lead to a different page.

Thanks for any help you can give me :)

2010-05-30: Saeef said:
Hello Bill,

Thanks for the great tutorial. I've searched through all the comments but can't find a solution to my problem. I'm trying to making a multiple drag and drop game.

I've trying to create a game where users have 10 different objects (prod1, prod2, prod3….prod10) for 10 different Targets (targ1, targ2, targ3….targ10). Also have another target(final_target) for all of these 10 objects. First the 10 object should drop into the corresponding target. After then these object can be drop into the final target. If anyone drop the object into the wrong target it should go back to the original position. Also anyone want to drop the objects into the final_target without dropping it to the corresponding target it will be back to the second original position.

e.g, prod1 have two corresponding target name targ1 and final_target. First, the user need to drop the prod1 into trag1(if prod1 dose not drop into trag1 it will come back to its original position ). After prod1 drop into trag1, then user can drag the prod1 to the next target name final_target(if the prod1 dose not drop into the final_target it will go back to the targ1). Also anyone can not drop the prod1 into final_target without dropping the prod1 to targ1.

Please, help me to do this.
Thanks.



2010-06-02: Annabel Stewart said:
Hi there,
I've been really puzzled with my flash project. I have used the wonderful code above which has helped me hugely.

I'm wanting to enable the objects to scroll as there is a large number of them and don't fit on the movie.

I've tried using the scroll pane. Once the objects are link to that the don't seem to work when wanting to drag them to the target.

Do you have any suggestions?

Thanks

Annabel

2010-06-02: Bill Trikojus said:
if your movieclips are inside a scrollpane component, you will have to update the code to include the scrollpane in the path. Do a google search for how to target content inside a scrollpane.
Bill
iStaySafe - Emergency App for iPhone
--------
App to track my kids


2010-06-15: Jose M. said:
Hi Bill. Congratulations for your tutorial and help.

I've used your code for ten objects over four targets. I read all comments but don't found any answer.
I want a x,y position for each object over each target. Could I do it without a large if..then..else code?

Thanks.

2010-06-16: Jose M. said:
Hi again. I find a solution based on another one up. I made an array with positions inside each object, in the same position than in the target vector, then I modified this:

clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged = false;

for (i=0; i targ = targArray[i];

if (eval(this._droptarget) == targ) {

this.myFinalX=clip.PosX[i];
this.myFinalY=clip.PosY[i];

this.onTarget = true;
break;
} else {
this.onTarget = false;
}
}
}

thanks for the code again.

2010-07-05: Alex said:
Try to help me with this question--please email me at alex.kolozsy@yahoo.com

I am trying to make it towhere when you drag the item over the target, it goes to a frame in scene 1. i've tried using gotoAndStop("1",2)... but then it won't even register the drop target. Pretty much what I want it to say when you drag the object over the target is in scene 1 frame 2, not inside the movieclip. I need to know how to code it towhere when you drag the object over the target it goes to another frame in scene 1, instead of inside the movieclip. Please email any answers to me--thanks.

2010-08-17: Tom said:
Hi, Great tutorial, many thanks.

I have multiple targets (4) with 4 items to correlate to each, how can I get it so that each of the targets goes to a different state when one of the objects is rolling over?

Thanks

Tom

2010-10-11: james said:
Hey Bill,
I`ve read all the posts and am having a tough time with multiple clips and only 1 target. any help with this. I have two records and one player and want them both to snap to it. I saw the offset post and couldn`t get it to run.

2010-10-11: LibertyWarrior said:
Hello! Firstly Bill, your tutorial is amazing!! Thank you! I have incorporated your code into a simple 'child learning resources game' that I am creating. What I have on screen is four (4) Character Sprites and four (4) targets that are made invisible using the alpha effect set to zero (0). For every Character Sprite is an allocated target. The idea of the simple game, is that the user must click and drag each the character sprites and place them inside of a car. If the user drops the character sprites into the right spot into the car (where the invisible targets are located), then the sprites will snap to their respected targets as intended. This all works as intended (thank you again!). From here though, I have the question on screen that says something similar to 'are the people in the car?' and a button that says yes. What I need is, when the user click on the yes button, that the game will check if all the sprites have been dragged and dropped onto their respected targets in the car, if this is true, then the game should move onto the next label in the scene (i.e. the next portion of the game), however if the user clicks yes, and the sprites are not snapped to their respected targets, then the drag and drop portion of the game should simply just loop and ask the question again. Perhaps you may be able to provide me with some help on how to go about doing this? The code is as follows (which is basically just your code :D)

stop();


function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
this.beingDragged = true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged = false;
if (eval(this._droptarget) == targ) {
this.onTarget = true;
targ.gotoAndStop(2);
} else {
this.onTarget = false;
targ.gotoAndStop(1);
}
};


clip.myHomeX = clip._x;
clip.myHomeY = clip._y;

clip.myFinalX = targ._x;
clip.myFinalY = targ._y;


clip.onEnterFrame = function() {
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}


dragSetup(woman_mc,womanTarget_mc);
dragSetup(man_mc,manTarget_mc);
dragSetup(baby_mc,babyTarget_mc);
dragSetup(bag_mc,bagTarget_mc);


yes_btn.onRelease = function() {
(NOT SURE WHAT KIND OF CHECKS TO PLACE HERE)
};

2010-10-13: Alan said:
Bill, most interesting tutorial as is the ensuing interaction with your audience. I'm still learning and am trying to apply your examples to my situation where in my main movie, my code creates an empty movie clip, positions it on stage and loads a movie (user log in). I want this movie clip to be draggable.
The Flash 8 AS2 code looks like this:
createEmptyMovieClip("launcherHolder", 600);
var launcher_mcl:MovieClipLoader = new MovieClipLoader();
launcherHolder._x = 200;
launcherHolder._y = 200;
launcher_mcl.loadClip("LogIn.swf", launcherHolder);

launcherHolder.onPress=function()
{
trace("start drag");
startDrag(launcherHolder);
}
launcherHolder.onRelease=launcherHolder.onReleaseOutside=function()
{
trace("stop drag");
launcherHolder.stopDrag();

The clip is not draggable and I never see the trace. Any clues?


2010-10-13: Alan said:
SOLVED! When loading a swf, you have to wait for the movie to complete loading before you can attach handlers such as onPress to it.

What's happening is that you're attaching handlers to the clip you're loading into, which are being overwritten by the movie that you're loading, which happens sometime later.

The most common way to handle this is to use the "MovieClipLoader" class, which will generate events when the movie is completely loaded.

Thanks Duane at chumbysphere forum.


2010-10-27: Dan said:
I have used the as2 version with modifications many times. Now I'm working with the as3 version. Need to set it up so that a single drag clip can be valid for 3 or more targets. Please help

2010-10-29: melvin said:
i'm as noob here . i would like to gotoAndStop on another frame after i had drag all the items to the targets. please help... below is my code.


function dragSetup(clip, targArray) {
clip.onPress = function() {
startDrag(this);
this.beingDragged = true;
green_off.attachMovie("button_green_off", "newname1", 1);
red_off.attachMovie("button_red_off", "newname1", 1);
};

clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged = false;
for (i=0; i targ = targArray[i];
if (eval(this._droptarget) == targ) {
this.myFinalX=targ._x
this.myFinalY=targ._y
this.onTarget = true;
targ.gotoAndStop(2);
this.enabled = false;
_root.total = _root.total + 100;
my_bar._xscale = my_bar._xscale + 69;
my_bar_outline._xscale = my_bar_outline._xscale + 69;
my_bar_shadow._xscale = my_bar_shadow._xscale + 69;
green_off.attachMovie("button_green_on", "newname1", 1);


break;

}

else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
red_off.attachMovie("button_red_on", "newname1", 1);
}



}
};



//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;

clip.myFinalX = 0;
clip.myFinalY = 0;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;


//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;

}
};
}

allTargets1 = new Array(targetCircle1);
allTargets2 = new Array(targetCircle2);
allTargets3 = new Array(targetCircle3);
allTargets4 = new Array(targetCircle4);
dragSetup(circle1_mc,allTargets1);
dragSetup(circle2_mc,allTargets2);
dragSetup(circle3_mc,allTargets3);
dragSetup(circle4_mc,allTargets4);

2010-11-14: Na'il said:
Hey this is nice! This was very helpful, but how would i incorporate a tween to come back in as3?

2010-12-14: JP Fuam said:
Hello there,

I actually would like to deduct my calculation if the person drag out from the position. "theRight" must be minus right? I'm not sure how to write on it. Can you guild be on this. Thank you.

Here's is my full working code.

function dragSetup(clip,targ,targ1,targ2) {
myCounter=0 ;
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.gotRight=false;
this.beingDragged=false;
theDrop=eval(this._droptarget);
if ( theDrop == targ || theDrop == targ1 || theDrop == targ2) {
this.onTarget = true;
theDrop.gotoAndStop(2);
//ease to middle of clip it was dropped on
this.myFinalX = theDrop._x;
this.myFinalY = theDrop._y;
this.gotRight=true;
if(this.gotRight){
myCounter++;
}
} else {
this.onTarget = false;
}
//I'll let you figure out which clips need to be reset
_root.targ.gotoAndStop(1);
}
};

clip.myHomeX = clip._x;
clip.myHomeY = clip._y;

clip.onEnterFrame = function() {

if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;

} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}

dragSetup(s1,targets1,targets4,targets7);
dragSetup(s2,targets2,targets5,targets8);
dragSetup(s3,targets3,targets6,targets9);
dragSetup(s4,targets1,targets4,targets7);
dragSetup(s5,targets2,targets5,targets8);
dragSetup(s6,targets3,targets6,targets9);
dragSetup(s7,targets1,targets4,targets7);
dragSetup(s8,targets2,targets5,targets8);
dragSetup(s9,targets3,targets6,targets9);


2010-12-14: Bill Trikojus said:
I'm not sure what you mean. Might be best if you post this on actionscript.org
Bill
Emergency App for iPhone
--------
App to track my kids


2010-12-15: JP Fuam said:
Dear Bill,

I actually wanted to lock the item in the place where the item has place in the target. Don't let the ppl to drag again after putting on the right target.

Can help me?

2010-12-15: JP Fuam said:
I want it to snap on the place and count 1 time. Thank you.

2010-12-15: Bill Trikojus said:
You can turn off an event function by setting it to null

eg

//inside the onRelease, have checked and detected drop on target
this.onPress=null;
this.onRelease=null;
Bill
Emergency App for iPhone
--------
App to track my kids


2011-01-27: Jim Beiruty said:
Hello Bill,

Your comments are so useful and it is a great way to learn. I am trying to create a way to teach kids how to learn numbers: flash showing numbers from 1 to 9
where three digits are missing. the person should then drag and drop the write
number in the right position.

1 3 4 6 8 9

2 5 7

When the person selects 2 for instance and place it in the wrong position, he will receive a wong message and 2 will go back. If it is placed in the right position, he will get a congratulations message.

I know it is too detailed but I think it is close to that you have saiid earlier.
Thanks very much and I wish to know how to do this in flash.

2011-01-27: Dan Antoniuk said:
I would just create an invisible movie clip alpha = 0 for targets over the areas you want the student to drag the item to. If it matches it would stay in the target, if not it would go back.
/*drag objects (clip), targets(target) input instance names for ex "dragNum2" would be the instance name of a movie clip containing a "2" it would be a dragable object, t1, t2, t3 would be your invisible (example t1.alpha = 0)target movie clips*/
dragSetup(dragNum2,t1);
dragSetup(dragNum5,t2);
dragSetup(dragNum7,t3);

for the negative feedback. You could create a short movie clip that has a stop(); action on the first frame and on the second frame place a frame label such as "ST" then place this code under the else statement after the
e.target.onTarget = false; line
incorrect_mc.gotoAndPlay("ST");
See tutorial code for specifics. This easy mod should work for you
This is for AS3 version of code

2011-02-05: jim Beiruty said:
Thanks Dan, I will do my best to learn AS3. Best regards

2011-02-20: Jim said:
Hi Bill,

Thanks for ALL THE FREE TUTORIALS, you are generous enough to share your knowledge:

This tutorial which is done in AS2 was just what I needed to learn Action Script that goes beyond the usual. Particularly the ease dragable objects.

I am facing some difficulty in Action Script 3 whereby I was able to allocate and error message when the objects did not match properly and comments when the user successfully finishes the task properly.
My problem is this: when incorporating the drag and drop with messages, within flash web site, the drag able objects seem to remain visible on each and every frame label or new page.
I can send you the swf file so you can see exactly what I mean. Could it be a problem related to levels since the function statements and the Listeners has part1 part2 etc in them.
example:
stop();

// the following functions are used by the buttons

function part1(Event:MouseEvent):void {
gotoAndStop("home"); // frame label must be inside quotation marks
}
function part2(Event:MouseEvent):void {
gotoAndStop("info");
}
function nextpage(myEvent:MouseEvent):void {
nextFrame();
}
function prevpage(myEvent:MouseEvent):void {
prevFrame();
}
home_btn.addEventListener(MouseEvent.CLICK, part1);
info_btn.addEventListener(MouseEvent.CLICK, part2);

next_btn.addEventListener(MouseEvent.CLICK, nextpage);
back_btn.addEventListener(MouseEvent.CLICK, prevpage);


2011-03-01: oren said:
Dear Sir,

How to make a copy on drag ,
(mean that when drag out item,
will appear another to drag )

Please show in AS2, Thank you.

2011-03-02: dan antoniuk said:
Well I would use this approach. Make all of the draggable clips on the stage invisible except the first one. Place them in seperate layers so they follow in the sequence you want. I am assuming you're dragging from the same place on the screen if you're not then the layer order won't matter. On the drag behavior in your script you will turn on the visibility of drag movie clip below it. I think in AS2 it is something like yourmovieclipname.visibiliy = true (or false). You could even put in an if else statement to sort through it for you. If (dragclip = yourfirstclip){secondclip.visibility = true;
}else if(dragclip = yoursecondclip){thirdclip.visibility = true;} and so on. Also you'll need to set the visibility of all the movie clips to false except the first dragabble clip on the first frame. Hope this helps

2011-03-02: dan antoniuk said:
Well I would use this approach. Make all of the draggable clips on the stage invisible except the first one. Place them in seperate layers so they follow in the sequence you want. I am assuming you're dragging from the same place on the screen if you're not then the layer order won't matter. On the drag behavior in your script you will turn on the visibility of drag movie clip below it. I think in AS2 it is something like yourmovieclipname.visibiliy = true (or false). You could even put in an if else statement to sort through it for you. If (dragclip = yourfirstclip){secondclip.visibility = true;
}else if(dragclip = yoursecondclip){thirdclip.visibility = true;} and so on. Also you'll need to set the visibility of all the movie clips to false except the first dragabble clip on the first frame. Hope this helps

2011-03-18: Ante said:
Great code.

When i drag the MC (little circle) close to the centre of the big circle it doesn't register and snaps back to the starting position.

Why would this happen?

thanks



2011-03-18: Dan Antoniuk said:
Look at the function "startDragging" under e.target.startDrag();
place a true in between the parenthesis. This will center the drag clip to your mouse. That should help your problem. Also you might want to add the code to bring the drag clip to the very highest leve of the screen while you are in the area. Try this code:

function startDragging(e:MouseEvent):void
{
//brings drag to top layer
clip.parent.setChildIndex (clip, clip.parent.numChildren-1);
//scales drag object during drag 1.5 is similar to 150%
//you'll also need to scale it back to 1 (100%) on your stopDragging function
clip.scaleX = 1.5;
clip.scaleY = 1.5;
//placing true in () is an option to the center of the drag clip to the mouse. This is assuming a registration point in the center
e.target.startDrag(true);
e.target.beingDragged = true;
}

hope this helps. Most issues are due to registration point locations or where the mouse is clicked when dragged. This helps out. Also if you have a weird shapped drag clip. You can draw a large square on the top layer within the movied clip mc itself. Then set the alpha of the square to 0. By doing so you will then be able to click anywhere on the object to select it. Hope these tips have helped.

2011-03-18: Ante said:
thanks again

could i send you the fla file?

its just not working out, and im know im sooo close.

thanks



2011-03-18: Ante said:
this is my code to date, so it all works fine, just the target is playing up.

stop();
function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}
dragSetup(circle_mc,targetCircle);
dragSetup(circle2_mc,targetCircle);
dragSetup(circle3_mc,targetCircle);
dragSetup(circle4_mc,targetCircle);

2011-03-18: Bill Trikojus said:
As Dan said, the registration point is important. Do both your circles have the crosshair in the middle?
Bill
Emergency App for iPhone
--------
App to track my kids


2011-03-18: Dan said:
Well it looks like you're in AS2 and my code is AS3 so I'm not sure if it would help. My file is at work so I won't be able to get it to you until Monday. I don't work on Fridays

2011-03-21: Ante said:
Would it matter if the MC is nested within another MC?



2011-03-21: Bill Trikojus said:
Yes
Bill
App to track my kids
--------
App to track my kids


2011-03-21: Ante said:
Well thats probably the problem.

I have the circles within another mc.

Still cant see a way around it.



2011-03-22: Dan said:
I've noticed that the users mouse position in relation to the dragged object can have an effect on how the script works. You can verifiy this by purposefully dragging your mouse on the draggable item in a specific location each time. Try dragging from each of the corners of the object or near the various areas since it is a circle. Anyway it is a factor. To solve this you can draw a square with an alpha of zero within the Movie clip on a seperate uppermost layer. That will make the square the selectable region though it won't be visible. You can do the same to your target mc. The registration point is taken by the lowermost mc so that is the one that you will want to center on the regpoint. Make sure both your target MC and draggable MC have their registrations set to the center. Also by having the code set up to center the clip on drage helps alot too. I will post my drag code for AS3 in the next post.

2011-03-22: dan said:
//Drag Drop functions AS3
function dragSetup(clip:MovieClip, targ1:MovieClip)
{

function startDragging(e:MouseEvent):void
{
//brings drag mc (clip) to top z layer
clip.parent.setChildIndex(clip, clip.parent.numChildren-1);
//scales the drag clip to 150%
clip.scaleX = 1.5;
clip.scaleY = 1.5;
//by placing true inside the () the clips are centered to the mouse on drag
e.target.startDrag(true);
e.target.beingDragged = true;

}

function stopDragging(e:MouseEvent):void
{

stopDrag();
//scales the drag clip back to 100%
clip.scaleX = 1;
clip.scaleY = 1;
e.target.beingDragged = false;
//the drop
var theDrop:MovieClip;
if (e.target.dropTarget != null)
{
theDrop = e.target.dropTarget.parent;
}
else
{
// no drop here
theDrop = null;

}

//accepted valid drop follows
if (theDrop == targ1)
{
e.target.onTarget = true;
//the variables below will store the clips end position
clip.myFinalX = theDrop.x;
clip.myFinalY = theDrop.y;
//do this if target is true
//this is a feedback mc you would have a different line of code on the next line depending on your needs
correct_mc.gotoAndPlay("ST");
}
else
{
e.target.onTarget = false;
//this is a feedback mc you would have a different line of code on the next line
//do this if target is false
incorrect_mc.gotoAndPlay("ST");
}

}

//event listeners for drag functions
clip.addEventListener(MouseEvent.MOUSE_DOWN,startDragging);
clip.addEventListener(MouseEvent.MOUSE_UP,stopDragging);
//the variables below will store the clips starting position
clip.myHomeX = clip.x;
clip.myHomeY = clip.y;

function slide(e:Event):void
{
if (! e.target.beingDragged && ! e.target.onTarget)
{
//adjust value of the divisor for speed of return to orgin (advise values from 1 very fast 30 very slow)
e.target.x -= (e.target.x-e.target.myHomeX)/2;
e.target.y -= (e.target.y-e.target.myHomeY)/2;

//if the circle is dropped on any part of the target it slides to the center of the target
}
else if (!e.target.beingDragged && e.target.onTarget)
{
//adjust value of the divisor for speed of magnetic snap to center (advise values from 1 very fast 30 very slow)
e.target.x -= (e.target.x-e.target.myFinalX)/2;
e.target.y -= (e.target.y-e.target.myFinalY)/2;
}
progtxt.text = progressTotal;
if(e.target.onTarget && progressTotal == 11)
{
completed_mc.visible = true;
}
}
clip.addEventListener(Event.ENTER_FRAME,slide);
}
/*drag objects (clip), targets(target) input instance names
these are names of instances I used you would have more or less of them depending on your needs
you'll notice that there are only 5 targets yet 11 drag clips. in this case I had 4 targets that accepted two
valid drag clips ond one that accepted 3 clips as valid. This was a specific need for an ampp I was working on */
//drag set up
dragSetup(d1,T2);
dragSetup(d2,T5);
dragSetup(d3,T3);
dragSetup(d4,T4);
dragSetup(d5,T2);
dragSetup(d6,T1);
dragSetup(d7,T3);
dragSetup(d8,T5);
dragSetup(d9,T1);
dragSetup(d10,T4);
dragSetup(d11,T3);

2011-03-24: Nathan425 said:
hello there, sorry to be a nuisence, but im new to flash. Im currently making a drag and drop game in Actionscript 2.0, where the user has to drag a description to its correct picture. I have also added a timer in aswell so that the session times out if you take too long and takes you to a different screen (I used the drag and drop script that is found at the begging of this tutorial page).

I was just wondering if you knew how to put a scoring system into the game, so that if you drag the description to its correct picture, you gain a point, if you drag it somewhere wrong, you loose a point. And your points are displayed somewhere starting at 0. Do you have any idea on how to do this?

Also is it possible to make it so that when you have matched up all the cards correctly, the game automatically pogresses onto a new screen and shows you your points total from that game? and also if your timer runs out to 0, you are taken to your total points screen?

Thank you so much in advance

This is my script so far, of which I have used from this brilliant site.


stop();
end_btn.onRelease=function(){gotoandplay("endgame" );}

function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}
dragSetup(circle_mc,targetCircle);
dragSetup(circle2_mc,targetCircle2);
dragSetup(circle3_mc,targetCircle3);
dragSetup(circle4_mc,targetCircle4);
dragSetup(circle5_mc,targetCircle5);
dragSetup(circle6_mc,targetCircle6);
dragSetup(circle7_mc,targetCircle7);
dragSetup(circle8_mc,targetCircle8);
dragSetup(circle9_mc,targetCircle9);
dragSetup(circle10_mc,targetCircle10);

timer = 60;
countdown = function(){
timer--;
if(timer==0){
clearInterval(countdownInterval);
}
}
countdownInterval = setInterval(countdown,1000);

2011-03-25: Dan said:
Nathan-

You would set up a global variable and set it equal to an intial value. In AS3 you would place this up in the beggining of your script out of the fuction not in it. Here I will use an variable that I'll call "tracker" but you could use any name you want. For your score point display set up a dynamic text field on your stage and give it an instance name. I'll use one called scoreTxt

var tracker = 0;

scoreTxt.text = tracker;

now you'll simply add to the tracker value when a target is valid and minus a point when the target is invalid.

to add to the value:
//this will add 1 to the value each time

tracker ++;

place this in your script under the section when the user gets the right target.

Use this when the user drops over the target but has the wrong drag item for the target

tracker --;

This may not work for as2 so you could always try this:
//to add one to the variable
tracker = tracker +1;
//to minus on from the variable
tracker = tracker -1;

2011-03-25: Dan said:
Forgot about the last half of your question.

Here is what you do to do something after a certian score has been acheived.I'll use 10 as the score needed for the user to win.

if (tracker == 10)
{
//do something such as go to another area
gotoAndPlay("Winner");
//or something like displaying a new message
scoreTxt.text = "Congratualations, your a winner"
}

2011-03-28: Nathan425 said:
Thank you very much dan, thats brilliant :)

2011-03-31: Yumi said:
Esta Super-Hiper-Mega Genial!!!

2011-04-08: Gemma said:
Hey, im not so great on flash, but i have this tutorial working.
I was just wondering what the code would be for once all the objects have been placed on the correct target, for the next scene to play.

It is probably very obvious, but as i said im not so great on flash.

Any help would be great thanks :)

2011-04-09: Dan Antoniuk said:
Gemma-
This is for AS 3 code all on the first timeline
You would create a global variable and give it a name. For example
var = progressTotal;
This would go on the top of your code outside of any functions. Then inside your drag function on the section where you have the drag validated as acceptable you would add to the variable

//accepted valid drop follows
if (theDrop == targ1)
{
e.target.onTarget = true;
//the variables below will store the clips end position
clip.myFinalX = theDrop.x;
clip.myFinalY = theDrop.y;
//do this if target is true
if (progressTotal=10)
{
movieclipinstancenamehere.gotoAndPlay("YourFrameLabelNameHere");
}
//after a correct answer 1 is added to the variable
progressTotal++;
}
else
{
e.target.onTarget = false;
//this is a feedback mc you would have a different line of code on the next line
//do this if target is false
incorrect_mc.gotoAndPlay("ST");
}


2011-04-16: Marc said:
Hello, I am using AS2 and have multiple objects and 3 targets. I have a dynamic text box that keeps score, how do I move to another frame once the score is maxed out?

I tried this:

var tracker = 0; <- this is the name of my dynamic txt box
if (tracker == 20) {}; <- this is the max score
gotoAndStop("winner"); <- this is where I would want the player to go

But when I add this it just pushes the player to that frame, any ideas?

Thank you!


2011-05-19: Deborah Delin said:
Hi Dan, Thank you so much for this brilliant tutorial. I have one small problem. When I drag the small circle to the target it does not settle in the center of the target but glides up to top left of the large circle. I tried tweaking the numbers in this code you gave:

} else if (mousePressed == false && this.onTarget == true) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};

but it doesn't make any difference. How can I get it to center. I do hope you are still replying here and thank you so much in advance.

2011-05-19: Deborah Delin said:
Ok I figured it. I had to change the values for myFinalX. Duh!

Thanks again.

Deborah

2011-05-20: tebrown said:
Hey,

Ok so i have taken the AS3 version. What i am trying to do is two things.

Firstly, im trying to make it snap to the target, instead of floating into the circle itself.

Secondly, im trying to make it so that when the user puts one of the circles into the target, it will overwrite the original circle and make it go back to its position, and let the new circle take place into the targeted area.

Much help would be appreciated.
Here is the code i have:

function dragSetup(clip:MovieClip, targ:MovieClip) {

function startDragging(e:MouseEvent):void{

e.target.startDrag();
e.target.beingDragged=true;


}

function stopDragging(e:MouseEvent):void{

stopDrag();

e.target.beingDragged=false;
var theDrop:MovieClip
if (e.target.dropTarget!=null) {

theDrop=e.target.dropTarget.parent;
trace(theDrop);
} else {

theDrop=null;
}


if (theDrop == targ) {
e.target.onTarget = true;
targ.gotoAndStop(2);
} else {
e.target.onTarget = false;
targ.gotoAndStop(1);
}



}

clip.addEventListener(MouseEvent.MOUSE_DOWN,startDragging)
clip.addEventListener(MouseEvent.MOUSE_UP,stopDragging)


//the variables below will store the clips starting position
clip.myHomeX = clip.x;
clip.myHomeY = clip.y;
//the variables below will store the clips end position
clip.myFinalX = targ.x;
clip.myFinalY = targ.y;

function slide(e:Event):void{
if (!e.target.beingDragged && !e.target.onTarget) {
e.target.x -= (e.target.x-e.target.myHomeX)/2;
e.target.y -= (e.target.y-e.target.myHomeY)/2;
//if the circle is dropped on any part of the target it slides to the center of the target


this._x = this.homeX;
this._y = this.homeY;
}


}
clip.addEventListener(Event.ENTER_FRAME,slide)

}

dragSetup(circle_mc,targetCircle);
dragSetup(circle2_mc,targetCircle);


2011-07-08: Barrytron said:
Hey Bill! Great tutorial, it works great for me on the main timeline but once I place it inside a movieclip, dropTarget stops being recognised...any help? I know Gerald Kaute asked a similar question but alas I have checked and played with all manner or possibilities with the paths and nothing works! I am tearing my hair out over it! I have looked everywhere for a reason as to why this happens....I am doing something really stupid?

Thanks in advance!

2011-07-19: Theo Schuurmans said:
Hi,
I would like to make an interactive site/game in flash 8, Cs2 or Cs4 for educational purposes. I would like to ask a question on a screen and get the student to drag and drop pictures on to a specific area. Only when all the right pictures have been dropped in all the right places a move to the next screen (question) is allowed. This way the student can only complete the game when doing the right things, so to say. Alternatively a score is kept somewhere when the right drop has been made. This way a total amount of points can be awarded at the end of the game. Can anyone help me. I manage drag and drop but the rest is a mystery to me.

2011-08-11: Cartero said:
Thank you very much! really apprecciated!

2011-09-02: Eric said:
I want to make a drag and drop game with two targets. Both objects will have several objects dragged and dropped on them. I want the objects to vanish off the screen when they are dropped on the target or drop zone. However, certain objects can only be dropped on one target and certain objects can only go in the other drop zone or target. I want each drop from either target or drop zone to record each drop into one variable. When the variable has >11 items dropped in both drop zone combined I want to go to and play a certain keyframe. I tried to modify your code but it didn't work. I could get the object to be removed from the stage and I couldn't record them into a variable to get the movie to go to and play a certain keyframe after it was >11. Can you help me out?

2011-09-02: Dan said:
Your going to create a variable at the top of your page that will start at an initial value. This is usually 0 or 1 depending on your needs.

Second your code will have line on the section for the valid drop that will take that variable and add 1 to it. For example if your variable it "myCounter" you would have a line that is myCounter++; After that you'll need an if then statement that evaluates the variable and when it reaches the value you specify it will go to the frame you specify and the targets you.Example:
if(myCounter == 11){movieclipinstancenamehere.gotoAndPlay("FrameLabelNameWithinClip");}

if (theDrop == targ)
{
e.target.onTarget = true;
myCounter++;
}else if(myCounter == 11){movieclipinstancenamehere.gotoAndPlay("FrameLabelNameWithinClip");
}

2011-09-02: Dan said:
At the beginning of you code you will initiate a variable that is outside of the function. On your first line of code.

var myCounter = 0;

2011-09-02: Dan said:
Also within the function you would set the visibility of the correctly dragged clip to false.
if (theDrop == targ)
{
e.target.onTarget = true;
myCounter++;
}else if(myCounter == 11){movieclipinstancenamehere.gotoAndPlay("FrameLabelNameWithinClip");
}

if(theDrop == targ && clip == dragclipinstancenameONE)
{
dragclipinstancenameONE.visible = false;
}else if(theDrop == targ && clip == dragclipinstancenameTWO)
{
dragclipinstancenameTWO.visible = false;
}else if(theDrop == targ && clip == dragclipinstancenameTHREE)
{
dragclipinstancenameTHREE.visible = false;
}else if(theDrop == targ && clip == dragclipinstancenameFOUR)
{
dragclipinstancenameFOUR.visible = false;
}




2011-09-02: Eric said:
Thanks I will try it out and let you know how it works

This is for AS 2.0 right?


2011-09-02: Dan said:
Should work for AS2 Let me know if it doesn't. I'll check my mail over the weekend. Sorry my post wasn't complete I was working at the time.

2011-09-04: Andrada said:
I know that you guys are probably very professional and any help you could give me, I would appreciate it very much.
I'm using the script "drag & drop multiple targets",
with the swapDepth enabled, making the last clicked item to come in front of all the clips on the board.
So far, so good. But I have some of the draggers made up by the same small circles, stacked/glued together this time vertically (7 in a row) which make these new draggers taller than the majority. The problem is that when I try to drag and snap them, the bottom circle doesn't center into the middle of the dropping zone like the others. These new draggers center themselves with their vertical center into the center of the dragging zones.
I really need to have all these taller draggers centered themselves with the bottom cercle into the middle of the dropping targets, like the simple draggers made up by a single circle.
Is there a way to work around, applying a rule to the chosen individual objects without specifically applying to the main script? I mean when you drop the item, forcing it to snap a little bit higher in relation with Y coordinate of the dropping zones.
Or maybe there is another way to accomplish this?
Please, someone take a look at my script (and many, many thanks for this great tutorial)!

function dragSetup(clip, targArray) {
clip.onPress = function() {
startDrag(this); this.swapDepths(_root.getNextHighestDepth());
this.beingDragged = true;
};
clip.onRelease=clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged = false;
for (i=0; i targ = targArray[i];
if (eval(this._droptarget) == targ) {
this.myFinalX=targ._x
this.myFinalY=targ._y
this.onTarget = true;
_root.targ.gotoAndStop(2);
break;
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;

clip.myFinalX = 0;
clip.myFinalY = 0;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}
allTargets = new Array(targetCircle1, targetCircle2, targetCircle3);
dragSetup(circle1_mc,allTargets);
dragSetup(circle2_mc,allTargets);
dragSetup(circle3_mc,allTargets);

2011-10-23: Josefina said:
Hello, i've looked all over the forum but can't fix my problem, (i'm a begginer as well)
All 4 of my clips are draggable to multiple targets, so far everything is working

but i need it to "gotoandStop" when ALL the clips are in a "correct" target, nothing should happen when the clips are in incorrect target.

something like:
if clip1 is in target1 and clip2 is in target2 and clip3 is in target3 and clip4 is in target4 ... GoTo andStop

2011-10-25: Ronald said:
Hi, Great tutorial and very helpful. I learned a lot.

However i have a problem with the multiple version.

I used the sample file of the single version without the function and copied the code of the multiple one.
The targetCircle doesn't change colour.

I've used my own versions of this code but it didn't work so I though I'd take it exactly from this tutorial
but it still doesn't work. Am I missing something?

I couldn't check the multiple version sample file as after downloading it it doesn't seem to open in flash CS5.

2011-10-25: Ronald said:
I just found your second file. Just need to apply the same thing to my code now.

2011-10-29: Sindy Ramasawmy said:
I would like to drag a specific amount of object in a set. Get a response if the amount is correc and also if the amount is wrong. what is the code for that please!!!

2011-11-10: Megan said:
I am working on getting a drag and drop test to work. It has multiple drag items with one drop target,the part that i am having trouble with is I want each draggable variable to have a number attached to it. So, that when you drag and drop each variable that applies into the drop target. When you click submit you would then be able to add up to variable in the drop target to equal a response.
Here is what I have so far:
//Drag 'n Drop items into one drop target
function dragSetup(clip:MovieClip, targ:MovieClip) {

function startDragging(e:MouseEvent):void{
e.target.startDrag();
e.target.beingDragged=true;
}
function stopDragging(e:MouseEvent):void{
stopDrag();
e.target.beingDragged=false;
var theDrop:MovieClip

if (e.target.dropTarget!=null) {
theDrop=e.target.dropTarget.parent;
trace(theDrop);
} else {
theDrop=null;}

if (theDrop == targ) {
e.target.onTarget = true;
targ.gotoAndStop(2);
} else {
e.target.onTarget = false;
targ.gotoAndStop(1);
}
}

clip.addEventListener(MouseEvent.MOUSE_DOWN,startDragging)
clip.addEventListener(MouseEvent.MOUSE_UP,stopDragging)


//the variables below will store the clips starting position
clip.myHomeX = clip.x;
clip.myHomeY = clip.y;
//the variables below will store the clips end position
clip.myFinalX = targ.x;
clip.myFinalY = targ.y;
}
dragSetup(question1,questionmatch);
dragSetup(question2,questionmatch);
dragSetup(question3,questionmatch);
dragSetup(question4,questionmatch);
dragSetup(question5,questionmatch);
dragSetup(question6,questionmatch);
dragSetup(question7,questionmatch);
dragSetup(question8,questionmatch);

//These are the numbers that I want to be assosiated with each variable
var question1: Number = 1
var question2: Number = 1;
var question3: Number = 1;
var question4: Number = 3;
var question5: Number = 2;
var question6: Number = 4;
var question7: Number = 4;
var question8: Number = 2;
}


//Submit Buttons
function submitClick( submitEvent:MouseEvent ):void
{
if( submitEvent.target == submitBtn)
{
//handle the event
if (questionmatch >= 00 && questionmatch =< 2){
response= gotoAndStop( "clutch");
{else if (questionmatch >= 3 && questionmatch =< 6){
response= gotoAndStop("brief");
{else if (questionmatch >= 7 && questionmatch =< 9){
response= gotoAndStop( "big");
{else if (questionmatch >= 10 && questionmatch =< 18){
response= gotoAndStop("garbage")
}
}
submitBtn.addEventListener( MouseEvent.CLICK, submitClick );

2011-11-11: Dan said:
Megan-
Based on what you asked for this is what I came up with my changes are in red :
var score = 0;
submitBtn.addEventListener( MouseEvent.CLICK, submitClick );

//Drag \\\'n Drop items into one drop target
function dragSetup(clip:MovieClip, targ:MovieClip) {


function startDragging(e:MouseEvent):void{
e.target.startDrag();
e.target.beingDragged=true;
}
function stopDragging(e:MouseEvent):void{
stopDrag();
e.target.beingDragged=false;
var theDrop:MovieClip

if (e.target.dropTarget!=null) {
theDrop=e.target.dropTarget.parent;
trace(theDrop);
} else {
theDrop=null;}

if (theDrop == targ) {
e.target.onTarget = true;
targ.gotoAndStop(2);
/*this is where the drop has been validated as correct. Now we just short/check to see which drag movie clip has been dropped and add the correct value to a variable called “score” clip is always the current movie clip that has been dropped. Your question1, question2 etc are you drag clip instance names not variables*/
If(clip == question1 || clip == question2 || clip == question3)
{
/*score ++ will add one to the score variable if the drag instance is question 1, question 2 or question 3 “||” is logical or */
score ++;
}else if (clip == question5 || clip == question8)
{
score = score + 2;
}else if (clip == question4)
{
score = score + 3;
}else if (clip == question6 || clip == question7)
{
score = score + 4;
}

} else {
e.target.onTarget = false;
targ.gotoAndStop(1);
}
}

clip.addEventListener(MouseEvent.MOUSE_DOWN,startDragging)
clip.addEventListener(MouseEvent.MOUSE_UP,stopDragging)


//the variables below will store the clips starting position
clip.myHomeX = clip.x;
clip.myHomeY = clip.y;
//the variables below will store the clips end position
clip.myFinalX = targ.x;
clip.myFinalY = targ.y;
}
// “question1” is your drag mc instance name, “questionmatch” is your target mc instance name
dragSetup(question1,questionmatch);
dragSetup(question2,questionmatch);
dragSetup(question3,questionmatch);
dragSetup(question4,questionmatch);
dragSetup(question5,questionmatch);
dragSetup(question6,questionmatch);
dragSetup(question7,questionmatch);
dragSetup(question8,questionmatch);


}


//Submit Button
function submitClick(Event:MouseEvent ):void
{
if( score == 1)
{
//do this if score is 1
}else if(score == 2)
{
//do this if score is 2
}else if (score == 3)
{
//do this if score is 3
}else if(score == 4)
{
//do this if score is 4
{else if(score == 5)
{
// and so on
}
}





2011-11-11: Megan said:
Dan-
Thank You so much for your help!
However, I am still getting a syntax error.
I've tried the code a few different ways and the part that i keep getting hung up on is the "submit button".
Can I get your help one more time???
Here are the two different versions I have tried:

//Submit Button
function submitClick(Event:MouseEvent ):void
{
if( score == 1)
{
//do this if score is 1
}else if(score == 2)
{
//do this if score is 2
}else if (score == 3)
{
//do this if score is 3
}else if(score == 4)
{
//do this if score is 4
}else if(score == 5)
{
//do this if score is 5
}else if(score == 6)
{
//do this if score is 6
}else if(score == 7)
{
//do this if score is 7
}else if(score == 8)
{
//do this if score is 8
}else if(score == 9)
{
//do this if score is 9
}else if(score == 10)
{
//do this if score is 10
}else if(score == 11)
{
//do this if score is 11
}else if(score == 12)
{
//do this if score is 12
}else if(score == 13)
{
//do this if score is 13
}else if(score == 14)
{
//do this if score is 14
}else if(score == 15)
{
//do this if score is 15
}else if(score == 16)
{
//do this if score is 16
}else if(score == 17)
{
//do this if score is 17
}else if(score == 18)
{
//do this if score is 18
}else if(score == 19)
}
submitBtn.addEventListener( MouseEvent.CLICK, submitClick );

//VERSION 2

//Submit Button
function submitClick(Event:MouseEvent ):void
{
if( score == 1)
{
//do this if score is 1
}else if(score == 2)
{
//do this if score is 2
}else if (score == 3)
{
//do this if score is 3
}else if(score == 4)
{
//do this if score is 4
}else if(score == 5)
{
//do this if score is 5
}else if(score == 6)
{
//do this if score is 6
}else if(score == 7)
{
//do this if score is 7
}else if(score == 8)
{
//do this if score is 8
}else if(score == 9)
{
//do this if score is 9
}else if(score == 10)
{
//do this if score is 10
}else if(score == 11)
{
//do this if score is 11
}else if(score == 12)
{
//do this if score is 12
}else if(score == 13)
{
//do this if score is 13
}else if(score == 14)
{
//do this if score is 14
}else if(score == 15)
{
//do this if score is 15
}else if(score == 16)
{
//do this if score is 16
}else if(score == 17)
{
//do this if score is 17
}else if(score == 18)
{
//do this if score is 18
}else if(score == 19)
}
submitBtn.addEventListener( MouseEvent.CLICK, submitClick );

2011-11-12: Dan said:
Looks like your last entry is the problem

}else if(score == 19)
{
//do this
}
}else{
e.targer.onTarget = false;
targ.gotoAndStop(1);
}
}

2011-11-22: Simon said:
Nice code!

Could you help me to add one more thing to tis code?

If I have 4 targets to drag to targets and I want somting to hapen after ALL of them are finished. Like a "victory"

This code made it victory after just one circle was draged.

if (!e.target.beingDragged && e.target.onTarget){
victory.gotoAndStop(2);
}

Please help me :)





2011-11-22: danantoniuk said:
outside of the drag and drop function create a variable called "totalCount" or another name if you prefer. Set it equal to 0. ex
var totalCount = 0;

if(!e.target.beingDragged && e.target.onTarget){
totalCount ++;
if(totalCount == 4)
{
victory.gotoAndStop(2);
}
}

2011-11-23: Simon said:
I cant get it to work :/ I have pasted it in a few different places but none of them work :/ are you sure the code should work?

2011-11-30: Vladimir said:
Thanks!! A lot friend great help to me!!! :)
cheers!!!!!!!!!!!

2011-12-16: hemanth said:
Hi i like to insert a timer in a drag&drop file.
And the timer should stop when it is dropped in the currect location .
please would anyone tell me the script for this or mail it to this mail id hemanthrj4@gmail.com

2012-02-04: Cathy said:
Hi I have made a drag and drop screen after much online searching. Is it possible to make the draggable items copyable and draggable.
Eg three different coloured shapes that the user could keep going back to to build up a picture.
Thanks for your time.
Cathy

2012-02-09: Dan said:
Cathy I'm a little unclear as to what the final output drawing would be. The key to your solution is to update your drawing function each time the user drags the item to the target. The feedback or result should be done from the area in the drag function for when someone would normally get and "incorrect feedback" That way the original draggable clip will return to it normal position but the action will update the drawing when the person drags and releases over the target.

2012-02-09: Dan said:
//This is AS3 Code
//Drag Function
//This example is the most basic type of exclusive set, that is each drag item has only one unique correct target
function dragSetup(clip:MovieClip, targ:MovieClip)
{
clip.startRotation = clip.rotation;
function startDragging(e:MouseEvent):void
{

e.target.startDrag(true);
//true option centers the mouse on the clips registration point;
//reg point on target and drag clip needs to be centered withing flash during authoring
//brings drag mc (clip) to top z layer
clip.parent.setChildIndex(clip, clip.parent.numChildren-1);
clip.rotation = 0;
e.target.beingDragged = true;

}
function stopDragging(e:MouseEvent):void
{
stopDrag();
e.target.beingDragged = false;

//just turns off all highlighted clips on stop drag
HighlightAssistOff();

//the drop
var theDrop:MovieClip;
if (e.target.dropTarget != null)
{
theDrop = e.target.dropTarget.parent;
//trace(theDrop);
}
else
{
// no drop here
theDrop = null;
}

if (theDrop == targ)
{
e.target.onTarget = true;
//do this if target is true



}
else
{
e.target.onTarget = false;
//otherwise do this
//what you want to do when false by default the clip returns to the orgin
//YOUR REVEAL FUNCTION FOR THE DRAWING WOULD BE CALLED FROM HERE
//NORMALLY THIS IS WHERE YOU WOULD PUT AN INCORRECT FEEDBACK FUNCTION
//BUT IN YOUR CASE YOU WANT TO RE-USE THE ORIGINALLY DRAGGED ITEM OVER AGAIN
//BY PLACING THE FUNCTION HERE THE FUNCTION WILL EXECUTE THEN THE DRAG CLIP
//WILL RETURN TO IT'S ORGIN

}

}

clip.addEventListener(MouseEvent.MOUSE_DOWN,startDragging);
clip.addEventListener(MouseEvent.MOUSE_UP,stopDragging);
//the variables below will store the clips starting position;
clip.myHomeX = clip.x;
clip.myHomeY = clip.y;
//the variables below will store the clips end position
clip.myFinalX = targ.x;
clip.myFinalY = targ.y;

function slide(e:Event):void
{
if (! e.target.beingDragged && ! e.target.onTarget)
{
//adjust value of the divisor for speed of return to orgin (advise values from 1 very fast 30 very slow)
e.target.x -= (e.target.x-e.target.myHomeX)/5;
e.target.y -= (e.target.y-e.target.myHomeY)/5;

//if the circle is dropped on any part of the target it slides to the center of the target
}
else if (!e.target.beingDragged && e.target.onTarget)
{
//adjust value of the divisor for speed of magnetic snap to center (advise values from 1 very fast 30 very slow)
e.target.x -= (e.target.x-e.target.myFinalX)/10;
e.target.y -= (e.target.y-e.target.myFinalY)/10;
}

}
clip.addEventListener(Event.ENTER_FRAME,slide);
}

//Drag set up create target mc on the stage and dragabble objects place them where you want. Give them matching names to the set up below. Add or delete lines as needed depending on how many items you have

//drag objects (clip) ex D1, targets(target) ex T1 input instance names
dragSetup(D1,T1);
dragSetup(D2,T2);
dragSetup(D3,T3);
dragSetup(D4,T4);
dragSetup(D5,T5);
dragSetup(D6,T6);
dragSetup(D7,T7);
dragSetup(D8,T8);

function resetClip(clip)
{
clip.x = clip.startX;
clip.y = clip.startY;
clip.rotation = clip.startRotation;
clip.beingDragged = false;
clip.onTarget = false;
}

2012-02-14: nikolaou said:
Hello. Great tutorial!
What I would additionally try to do is to change the color of the target when the user drops in the right object...please help!

2012-02-14: nikolaou said:
The problem is that when I use this code:


circle_mc.onPress=function(){
startDrag(this);
}
circle_mc.onRelease=circle_mc.onReleaseOutside=function(){
stopDrag();
if (this._droptarget == "/targetCircle") {
this.onTarget=true;
_root.targetCircle.gotoAndStop(2);
}else{
this.onTarget=false;
_root.targetCircle.gotoAndStop(1)
}
}
circle_mc.myHomeX=circle_mc._x;
circle_mc.myHomeY=circle_mc._y;

circle_mc.onMouseDown=function(){
//this variable tells us if the mouse is up or down
mousePressed=true;
}
circle_mc.onMouseUp=function(){
mousePressed=false;
}
circle_mc.onEnterFrame=function(){
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)
if(mousePressed==false&&this.onTarget==false){
this._x-=(this._x-this.myHomeX)/5;
this._y-=(this._y-this.myHomeY)/5;
}
}

it works fine, though the object doesn't move to the center of the target.

But when I insert the "final" code


function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}
dragSetup(circle_mc,targetCircle);

unfortunately the target doesn't change color...

2012-02-15: dan said:
create a variable for each color you want to use. The initial value of the variable will reside outside of the function. For example:
var colorValue=1;
Change the value of the variable when the answer is correct. This could be done several ways such as colorValue = ++; This would be placed within the drag function under the section where a drop is correct. The ++ just is short hand to add one to the current value of the colorValue variable. So if the current value of the colorValue is 3 the new value would become 4 when the answer is correct. Then you would need to also create an if then statement to sort it out:
if (colorValue==2)
{
yourTargetMC.gotoAndStop("green");
}else if (colorValue==3)
{
yourTargetMC.gotoAndStop("blue");
}else if(colorValue==4)
{
yourTargetMC.gotoAndStop("red");
}
and so on
each color could reperesent a frame label within you target movie clip. Or you could just change the color of the clip if it is a basic shape via AS code.

2012-03-16: Sarah said:
Hey. This is the best tutorial for this particular area I've come accross! Thanks so much. Any chance I could ask you how to sort a reset button? Am making adrag and drop dressing up game for kids and need it to restart or be bale to be reset after it's done as it will be in a public place and used a lot! Thanks so much!

2012-03-16: Dan A said:
You would assign a variable value to each clothing item. When the total reaches the total of all of the items the reset function you write would be called. For example if you have a hat, shirt, pants, pair of socks, and pair of shoes that have been dragged on the charcter the application would be reset. You probable would want a short delay and congratulations message "Great Job". In my example there are five cloting items and you could simply set up a global variable called something like "clothingItemCounter" and set its value = 0. Then within your drag and drop function just add one (++) to the variable each time a clothing item is dragged to a target. See below code:

Var clothingItemCounter = 0;
function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ) {
this.onTarget = true;
clothingItemCounter ++;
if (clothingItemCounter == 5)
{
finalMovieClipInstanceName.visible = true;
//or whatever other action you choose to occur when the activity is completed
clothingitemCounter = 0:
}
} else {
this.onTarget = false;
//place actions you want to occur when the target is missed.
}
};


2012-03-23: sarah said:
Hey,
Thanks for replying to query.
I'm a designer who isn't as familiar with code as I should be so I tried to add what you suggested (and I'm sure if I handled it properly it would have worked) but I botched it somehow.If you could I'd appreciate the help. Otherwise I'll have a great drag and drop game that can only be used once! :)Thanks,
Sarah

so here's the story so far.....

Where do I put the above code? I have one area of action script based on your code. This is what I have:

function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ) {
this.onTarget = true;
_root.targ.gotoAndStop(2);
} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);
}
};
//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
clip.onEnterFrame = function() {
//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/5;
this._y -= (this._y-this.myHomeY)/5;
//if the circle is dropped on any part of the target it slides to the center of the target
} else if (!this.beingDragged && this.onTarget) {
this._x -= (this._x-this.myFinalX)/5;
this._y -= (this._y-this.myFinalY)/5;
}
};
}
dragSetup(mclolly,targetlolly);
dragSetup(mcglasses,targetglasses);
dragSetup(mcscarf,targetscarf);
dragSetup(mchat,targethat);
dragSetup(mcletter,targetletter);
dragSetup(mcshoeleft,targetshoeleft);
dragSetup(mcshoeright,targetshoeright);
dragSetup(mcjeans,targetjeans);

And this works. All items drag and drop and look great. If I create a variable in the first place do I make it a movie symbol and them in it's instance name call it clothingitemcounter? I have 8 items in total. Do I put the variable and the finalmovieclip on the stage to be revealed if complete or where do I leave it. Can i put it in a seperate scene?

2012-03-24: dan said:
Sarah- Just declare your global variable outside of the drag and drop function

In this case just place it on the very first line top of the code

Var clothingItemCounter = 0;

This basically says to create a variable called clothingItemCounter and set it's initial value = 0

You will then need to place the if then statements in your code

if (eval(this._droptarget) == targ) {
this.onTarget = true;
//the ++ adds 1 to the current value of the clothingItemCounter variable when you drag a valid object and drop it over it's correct target 1 is added to the counter
clothingItemCounter ++;
if (clothingItemCounter == 5)
{
these actions only execute if the clothingItemCounter value is equal to 5
finalMovieClipInstanceName.visible = true;
this is where you would reset your items how you do it depends on how you built your application
//or whatever other action you choose to occur when the activity is completed
the variable clothingItemCounter is also reset to 0 after it reaches 5 so that the activity can reset back
clothingItemCounter = 0:
}
} else {
this.onTarget = false;
//place actions you want to occur when the target is missed.
}
};




2012-03-26: gyan said:
I made two targets and a valid movie clip to drop on any of one target. see the below code.

//++++++++ spects: drop object
//++++++++ target1 and target 2 are target areas.

spects.onPress = function ()
{
startDrag(this, false, rect._x, rect._y, rect._x + rect._width - this._width, rect._y + rect._height - this._height);
_root.org.textshow.gotoAndStop(1);

};
spects.onRelease = spects.onReleaseOutside = function ()
{
stopDrag ();
if(eval(this._droptarget)._name=="target1")

{
stopAllSounds();
this.onTarget = true;
_root.org.textshow.gotoAndStop(2);
spects.myFinalX = this._x;
spects.myFinalY = this._y;
trace("1");

}
else if(eval(this._droptarget)._name=="target2")
{
stopAllSounds();
this.onTarget = true;
_root.org.textshow.gotoAndStop(3);
spects.myFinalX = this._x;
spects.myFinalY = this._y;
trace("2");

}

else
{
this.onTarget = false;
_root.org.textshow.gotoAndStop(1);

}
};
spects.myHomeX = spects._x;
spects.myHomeY = spects._y;

spects.onMouseDown = function ()
{
mousePressed = true;
};
spects.onMouseUp = function ()
{
mousePressed = false;
};
spects.onEnterFrame = function ()
{
if (mousePressed == false && this.onTarget == false)
{
this._x = this._x - (this._x - this.myHomeX) / 5;
this._y = this._y - (this._y - this.myHomeY) / 5;
}
else if (mousePressed == false && this.onTarget == true)
{
this._x = this._x - (this._x - this.myFinalX) / 5;
this._y = this._y - (this._y - this.myFinalY) / 5;
}
};

code works fine alone but when i load the swf in main(container) then its not working.

can anyone help me to rectify the bug..
Thanks in advance.

2012-03-27: Sarah said:
Hi, I've had two very helpful and informative repliews to my qyuest to get mt drag and drop game to reset but still no joy. Any chance anyone would be willing to accept the .fla file to have a look under the hood? This is a student project with a fast approaching deadline. Thanks

2012-03-29: dan said:
Sarah go a head and send me the fla I will look it over. I am at home at the moment and only have cs4 at home so could you send the fla as a cs4 version


2012-04-02: sarah said:
hi dan, i emailed file on thursday to forums mail address which appears when i receive email notifications but realised the address is a noreply one. can you send me a mail and i can reply with attachment? or maybe you did get that mail? thanks

2012-04-02: dan said:
Sarah- I did not get the mail go ahead and send it to my address directly. danantoniuk@yahoo.com

2012-05-03: Juanjo said:
Hi, i'm using this code but i have a problem. When i load the movie in lvel 0, all works fine but when i load in level 1, the target seem not to exist... i think the problem is the notation "/" but i've tried parent, level, root, eval... anything works... the target seems to work only in level0... thanks for tutorial and code!


on (release) {
if (this._droptarget != "/casilla_sit_1")
{
_root.opc1 = 0;
}
if (this._droptarget == "/casilla_sit_1")
{
_root.opc1 = 1;
}
}


2012-08-09: michael said:
:D hi mine did perfect but on my second sticker (circle) it places it where the other circle is placed???

2012-08-10: dan said:
Juanjo- you can't have quotations here and a path instance name is all wrong.
Instead of using an instance name you want to refer to the currently dropped/dragged clip. This is simply "clip" in the function - do not place quotations around it. Camparisons to strings are not allowed. Also you are referring to _root which is no longer used in AS3. This function is AS3 not AS2.

if (this._droptarget != clip)
{
opc1 = 0;
}
if (this._droptarget == clip)
{
opc1 = 1;
}
}


What the the statement says translated in English is
if the item released over the drop target area clip is not equal to the current clip then set the value of the variable named opc1 equal to 0.

If the item released over the drop target area clip is equal to the current clip then set the value of the variable named opc1 equal to 1.

I have a feeling you really meant to send the playback head of the opc1 (assume this is a movie clip) to a specific frame depending on the outcome. To do this here is how you would write it. Otherwise if you were really trying to assign a value of a variable named opc1 you would do it as the above. This is what I think you meant to do:

if (this._droptarget != clip)
{

//comment there is no such thing as frame 0 so 1 is used
opc1.gotoAndPlay(1);
}
if (this._droptarget == clip)
{
//comment the movie clip opc1 is played from frame 2
opc1.gotoAndPlay(2);
}
}


2012-10-18: psychopeter said:
great tutorial thanks, One question tho, I have many objects that are in various movie clips, I'd like to use variables on them and so

var a=(_root).movieclip1.todrag;
var b=(_root).movieclip2.target;

I believe there is a issue with the droptarget where it won't register the var b ?

I have tried _droptarget == "b", "/b" and simple == b . How can I target a on object that is in other movieclip ?

Thanks !

2012-10-23: Ausan singh said:
Hello! frnds i want multiple dragging in one drop box...when all 3 will be dragged then that will be play another frame.
otherwise that will be stopped there
plz help me....:)

stop();

var score:Number=0;

function dragSetup(clip, targ) {
clip.onPress = function() {
startDrag(this);
this.beingDragged=true;
};
clip.onRelease = clip.onReleaseOutside=function () {
stopDrag();
this.beingDragged=false;
if (eval(this._droptarget) == targ) {
this.onTarget = true;
this._visible=false;
_root.targ.gotoAndStop(2);


} else {
this.onTarget = false;
_root.targ.gotoAndStop(1);

}

};

//the variables below will store the clips starting position
clip.myHomeX = clip._x;
clip.myHomeY = clip._y;
//the variables below will store the clips end position
clip.myFinalX = targ._x;
clip.myFinalY = targ._y;
clip.onEnterFrame = function() {

//all these actions basically just say "if the mouse is up (in other words - the clip is not being dragged)
// then move the MC back to its original starting point (with a smooth motion)"
if (!this.beingDragged && !this.onTarget) {
this._x -= (this._x-this.myHomeX)/2;
this._y -= (this._y-this.myHomeY)/2;

//if the circle is dropped on any part of the target it slides to the center of the target
}
else if (!this.beingDragged && this.onTarget) {
if(this.score==2)
{
gotoAndPlay("play");
}
else
{
this.score++;
}
}
};
}



dragSetup(dragMc1,targetMc);
dragSetup(dragMc2,targetMc);
dragSetup(dragMc3,targetMc);


2013-04-25: Paulina said:
Hi! Your tut. is great and helped me a lot. Although I've a problem. Your script work very well in first swf, but when I loaded it to another (navigation/main)swf on level 1 it crashed. Do you have any idea why and what can I do to fix it?
I'll be very graetfull for some guidelines :)

2013-05-11: Grega Jezersek said:
Hello

i have a multiple drag n drop in as 2.o and i would like it to autop play to the next frame when they are all alinged

can you help me

LP Grega

2013-05-11: Grega said:
Hello bill

i need a lil help

I i have mad a multiple drag n drop quiz and i dont know how to make it auto play to the nex frame when all the circles are on target

Thanks in advance

grega

2013-05-14: tma said:
Hi! thank you so much for this^-^

I have a question though. Is it possible to drag 2 clips simultaneously using this code?

I have 2 clips on different layers that I want to be dragged simultaneously. I need them to be dragged and dropped on the target at the same time.

I'm sorry, I'm a noob and I just can't figure it out.

Hope you can help.^-^



Post a comment

Garbage posts and SPAM will be deleted.

* Name:
* Email: (will not be made public)
* Comment:
* Reply Notification: