Home | Contact Us | FAQ | Search & Site Map | Link to Us
Sign In | Join | Other 45 Sites in Network
HomeAnnouncementsFree MagazinesWhite PapersSubmit Content
Discussion GroupsASP.NETWindows FormsLanguages.NET FrameworkVisual Studio.NET
Articles.NET FrameworkASP.NETToolsWindows Forms
.NET DirectoryOpen Source ProjectsUser GroupsWeb Resources
Related Topics
Visual Basic 6SQL ServerMS AccessOther DB ProductsMS Server ProductsMore Topics ...

.NET Forum / Languages / C# / July 2007

Tip: Looking for answers? Try searching our database.

The Tower OF Hanoi

Thread view: 
Enable EMail Alerts  Start New Thread
Thread rating: 
shaghayeghcute2003@yahoo.com - 04 Jul 2007 19:17 GMT
I'm currently trying to write The Tower Of Hanoi (http://
illuminations.nctm.org/ActivityDetail.aspx?ID=40) in C#.
I have a panel on the form and I draw pegs on the panel inside the
form class. I passed GraphicObject to drawDisk method in disk class to
draw disks' pictures.
I used MouseDown/Up/Move to move these disks on the panel.
I'm attaching some part of my code:

private void panel1_MouseDown(object sender,
System.Windows.Forms.MouseEventArgs e)
       {

           mouseLocation = new Point(e.X, e.Y);
           drag = true;
       }
      private void panel1_MouseMove(object
sender,System.Windows.Forms.MouseEventArgs e)
       {//p1 is the first peg
           ((Disc)p1.discsPile[0]).xLocation = e.X;
           ((Disc)p1.discsPile[0]).yLocation = e.Y;
           this.Invalidate();
           panel1.Invalidate();
        }

      private void panel1_MouseUp(object sender, MouseEventArgs e)
       {
           drag = false;
       }
When I try to move the disks on the panel, nothing happens
Could you please someone tell me what the mistake is?
I appreciate for your help in advance.
Göran Andersson - 04 Jul 2007 19:37 GMT
> I'm currently trying to write The Tower Of Hanoi (http://
> illuminations.nctm.org/ActivityDetail.aspx?ID=40) in C#.
[quoted text clipped - 25 lines]
>         }
> When I try to move the disks on the panel, nothing happens

Standard question #4:
No, "nothing" never happens. Exactly what is happening?

> Could you please someone tell me what the mistake is?
> I appreciate for your help in advance.

Have you verified that the xLocation and yLocation properties actually
change? Do you actually use the xLocation and yLocation properties when
drawing the discs? What does the Disc class and the xLocation and
yLocation properties look like?

Signature

Göran Andersson
_____
http://www.guffa.com

shaghayeghcute2003@yahoo.com - 04 Jul 2007 20:14 GMT
On Jul 4, 2:37 pm, G?ran Andersson <g...@guffa.com> wrote:
> shaghayeghcute2...@yahoo.com wrote:
> > I'm currently trying to write The Tower Of Hanoi (http://
[quoted text clipped - 43 lines]
>
> - Show quoted text -

Hi dear Andersson;
Thanks for your quick respond.
I put messgasebox.show inside the Panel1_MouseMove to show me the
xlocation and ylocation but it didn't print anything.
It seems MouseMove/Up/Down arenot executed at all.
I changed System.windows.Form.MouseEventArgs to MouseEventArgs, but it
didn't make difference.
What is your next suggestion?
Thanks;
Shaghayegh
Peter Duniho - 05 Jul 2007 00:04 GMT
> [...]
> When I try to move the disks on the panel, nothing happens
> Could you please someone tell me what the mistake is?

Well, it's hard to say, since you didn't post minimal-but-complete code.  
Given the code that you did post, my first suspicion is that you didn't  
actually subscribe those event handlers to correct events.  I admit, that  
doesn't seem plausible at the face of it, because your event handlers are  
named exactly as they would be if you'd double-clicked on the panel  
instance's events for them in the designer.  But the MouseMove handler in  
particular should definitely be changing the coordinates of the discs.  
The code's wrong, but _something_ should be happening.

Basically, the only way I see for _nothing_ to happen is if that event  
handler isn't called at all.

That said, you do have some other problems.  The two that specifically  
stand out are:

    * You don't use "mouseLocation" when changing the coordinates of the  
disc in question.  Consequence: the disc will "snap" to the mouse  
location, rather than just "sticking" to the mouse cursor wherever it  
happens to be
    * You don't check "drag" before changing the coordinates.  
Consequence: any movement of the mouse over the control will result in  
movement of a disc, whether the mouse button was pressed or not.

A third issue that will be a problem when you get around to actually  
trying to make this work correctly is that you aren't doing any  
hit-testing in MouseDown to figure out _which_ disc you should actually be  
moving.  I will assume for the moment that you're aware of that, and that  
the code is currently the way it is just so you can figure the other stuff  
out.

Now, all that said, here's the basic idea of how I think this should be  
done:

    private List<Peg> _pegs = new List<Peg>();
    Disc _discDragging;
    Peg _pegFrom;
    Point _pointDragStart;

    private void panel1_MouseDown(object sender, MouseEventArgs e)
    {
        foreach (Peg peg in _pegs)
        {
            // assumption: the Disc at index 0 is the top disc.  Check
            // only that disc, because you can't drag any other disc other
            // than the top one anyway
            Disc disc = peg.discsPile[0];

            // assumption: the Disc class has a property Bounds that gets
            // a Rectangle that is the extent of the Disc graphically.
            if (disc.Bounds.Contains(e.Location))
            {
                _discDragging = disc;
                _pegFrom = peg;
                _pointDragStart = e.Location;
                break;
            }
        }
    }

    private void panel1_MouseMove(object sender, MouseEventArgs e)
    {
        if (_discDragging != null)
        {
            // assumption: the Disc class has a property Location that  
gets/sets
            // the position of the Disc graphically (most likely the  
upper-left
            // corner of the Bounds rectangle, but that's not actually  
important
            // here)
            Point ptNew = _discDragging.Location;

            // offset the position by the same distance that the mouse has  
moved
            // since our last mouse event
            ptNew.Offset(e.Location - _pointDragStart);
            _discDragging.Location = ptNew;

            // update the "last mouse event" position
            _pointDragStart = e.Location;

            // Signal the panel to redraw
            panel1.Invalidate();
        }
    }

    private void panel1_MouseUp(object sender, MouseEventArgs e)
    {
        if (_discDragging != null)
        {
            // I'm going to leave a lot of stuff out here.  Hopefully, you  
can see
            // the basic idea from the code I did include and take it from  
here.
            // When the MouseUp event happens, you have to do some things:
            //     -- compare the disc's position to the peg locations, to  
figure
            //        out which peg the disc is being dragged to
            //     -- check the existing discs on that peg to make sure  
that the
            //        peg is a valid peg on which the disc can be dropped
            //     -- depending on the previous check, either remove the  
disc from
            //        its current peg (my field named "_pegFrom"),  
calculate the
            //        correct graphical position for the new peg, set it  
to that
            //        position and add it to the new peg, or simply  
calculate the
            //        correct graphical position for the original peg and  
put it back
            //        there.
            //     -- if you want to provide the user feedback regarding  
whether they
            //        have succesfully moved the discs from one peg to the  
other, this
            //        would be a good place to check that too

            _discDragging = null;
        }
    }

This is by no means the canonical way to do this.  There are variations on  
this theme that are all valid, depending on how you like the code to look  
and what specifically you are doing with the code.  But I think the above  
solution is pretty appropriate given your goals.

One thing I will mention: you appear to be storing your list of discs on  
each peg with the disc at index 0 being the top disc.  IMHO, it makes more  
sense to store the discs bottom-up, with the disc at index 0 being the  
bottom disc.  The reason being that it is more efficient when dealing with  
an array to add and remove things at the end, rather than the beginning,  
and all of the adding and removing happens at the disc that's at the top  
of the peg.  So making the disc at the top of the peg being the last in  
the array rather than the first is more efficient.

Pete

Free Magazines

Get these publications absolutely FREE for up to 12 months. There are no hidden fees and no obligation. Simply choose a title, complete the application form and submit it. Read more ...

Oracle MagazineNetwork ComputingComputer WorldBio-IT WorldeWeekInformation WeekInfosecurity
 
Sign In
Join
My Latest Posts
My Monitored Threads
My Blog
My Photo Gallery
My Profile
My Homepage

Start New Thread
Enable EMail Alerts
Rate this Thread



©2008 Advenet LLC   Privacy Policy - Terms of Use
This website includes both content owned or controlled by Advenet as well as content owned or controlled by third parties.