From 693c77cfe06a29fab8f027c94b4a2dcaed06e53c Mon Sep 17 00:00:00 2001
From: Tim Young <tim.young@lightsys.org>
Date: Tue, 6 Jun 2017 15:13:52 -0500
Subject: [PATCH] Initial drag of multiple items

---
 EduNetworkBuilder/Network.cs        | 23 +++++++++
 EduNetworkBuilder/NetworkBuilder.cs | 76 +++++++++++++++++++++++++++--
 EduNetworkBuilder/NetworkDevice.cs  |  5 ++
 3 files changed, 99 insertions(+), 5 deletions(-)

diff --git a/EduNetworkBuilder/Network.cs b/EduNetworkBuilder/Network.cs
index f61a9de..70287aa 100644
--- a/EduNetworkBuilder/Network.cs
+++ b/EduNetworkBuilder/Network.cs
@@ -392,7 +392,30 @@ namespace EduNetworkBuilder
             }
             return null;
         }
+        public List<NetworkDevice> DevicesInRectangle(Rectangle area)
+        {
+            NetworkDevice tDevice;
+            Point tPoint;
+            List<NetworkDevice> thelist = new List<NetworkDevice>();
 
+            foreach (NetworkComponent tItem in NetComponents)
+            {
+                if (tItem is NetworkDevice)
+                {
+                    tDevice = (NetworkDevice)tItem;
+                    int tsize = tDevice.Size;
+                    tPoint = tDevice.myLocation();
+                    if (tPoint.X + tsize >= area.X && tPoint.Y +tsize >= area.Y)
+                    {
+                        if (tPoint.X <= area.X + area.Width && tPoint.Y <= area.Y + area.Height)
+                        {
+                            thelist.Add(tDevice);
+                        }
+                    }
+                }
+            }
+            return thelist;
+        }
         public NetworkDevice ItemFromName(string hostname)
         {
             NetworkDevice tDevice;
diff --git a/EduNetworkBuilder/NetworkBuilder.cs b/EduNetworkBuilder/NetworkBuilder.cs
index 6bc5a41..7781ef3 100644
--- a/EduNetworkBuilder/NetworkBuilder.cs
+++ b/EduNetworkBuilder/NetworkBuilder.cs
@@ -47,6 +47,7 @@ namespace EduNetworkBuilder
         public Point LastMouseMovePos = new Point(-1, -1);
         private NetworkDevice ItemClickedOn = null;
         private List<NetworkDevice> ItemsSelected = new List<NetworkDevice>();
+        private Point OrigClickPoint = new Point(-1, -1);
 
         public BuilderWindow()
         {
@@ -919,7 +920,6 @@ namespace EduNetworkBuilder
             Point CenteredLocation = myNetwork.clickedPosCentered(e.Location);
             Point ClickLocation = myNetwork.clickedPos(e.Location);
             NetworkDevice ReleasedOn = myNetwork.ItemAtPosition(ClickLocation);
-            MouseIsDown = false;
             LastBackgroundImage = null;
             pbNetworkView.Image = null; //erase old highlight area
             LastMouseMovePos = new Point(-1, -1);
@@ -933,7 +933,6 @@ namespace EduNetworkBuilder
                 pbNetworkView_RightMouseUp(ReleasedOn, e);
                 return;
             }
-
             if (duration.TotalMilliseconds < 250)
             { 
                 //This mouse-up is part of a double-click operation. Do an edit
@@ -941,6 +940,54 @@ namespace EduNetworkBuilder
             }
             else
             {
+                if (MouseIsDown && ItemClickedOn == null && ItemsSelected.Count > 0)
+                {
+                    //We were dragging stuff.  All done now
+                    MouseIsDown = false;
+                    ItemsSelected.Clear(); //clear it so we stop moving these ones
+                    return;
+                }
+                if (MouseIsDown && ItemClickedOn == null)
+                {
+                    //We just finished dragging a select box
+                    //Put them all into the drag box.
+                    ItemsSelected.Clear();
+                    int sx;
+                    int sy;
+                    int swidth;
+                    int sheight;
+                    if (ClickedImageLocation.X > e.Location.X)
+                    {
+                        sx = e.Location.X;
+                        swidth = ClickedImageLocation.X - sx;
+                    }
+                    else
+                    {
+                        sx = ClickedImageLocation.X;
+                        swidth = e.Location.X - sx;
+                    }
+                    if (ClickedImageLocation.Y > e.Location.Y)
+                    {
+                        sy = e.Location.Y;
+                        sheight = ClickedImageLocation.Y - sy;
+                    }
+                    else
+                    {
+                        sy = ClickedImageLocation.Y;
+                        sheight = e.Location.Y - sy;
+                    }
+                    //Now we have a rectangle, but need to exchange numbers for numbers on the image
+                    Point topCorner = myNetwork.clickedPos(new Point(sx, sy));
+                    Point botCorner = myNetwork.clickedPos(new Point(sx + swidth, sy + sheight));
+
+                    Rectangle selectbox = new Rectangle(topCorner.X, topCorner.Y, botCorner.X - topCorner.X, botCorner.Y - topCorner.Y);
+
+                    ItemsSelected.AddRange(myNetwork.DevicesInRectangle(selectbox));
+                    Console.WriteLine("Selected " + ItemsSelected.Count + " items");
+                    MouseIsDown = false;
+                    return;
+                }
+                MouseIsDown = false;
                 if (selectedButton == "btnLink")
                 {
                     //We are making a link
@@ -1039,6 +1086,7 @@ namespace EduNetworkBuilder
         {
             Point location = myNetwork.clickedPos(e.Location);
             ClickedLocation = location;
+            OrigClickPoint = myNetwork.clickedPosCentered(e.Location);
             ClickedImageLocation = e.Location;
             //See if we have clicked on something
             ItemClickedOn = myNetwork.ItemAtPosition(location);
@@ -1061,7 +1109,7 @@ namespace EduNetworkBuilder
             myNetwork.Invalidate(oldrec);
 
             //set it to the new pos
-            toMove.ChangeLocation(NewPosition);
+            toMove.ChangeLocationUnsnapped(NewPosition);
             //tell it to draw
             toMove.Print(pbNetworkView.BackgroundImage, false);
             //invalidate
@@ -1075,12 +1123,30 @@ namespace EduNetworkBuilder
 
             Point CenteredLocation = myNetwork.clickedPosCentered(e.Location);
             Point MouseLocation = myNetwork.clickedPos(e.Location);
-            if (MouseIsDown && LastBackgroundImage != null && ItemClickedOn != null) //We are trying to drag something
+            if (MouseIsDown && LastBackgroundImage != null && ItemClickedOn != null && ItemsSelected.Count == 0) //We are trying to drag something
             {
                 //find where we are
                 DragItemToNewLocation(ItemClickedOn, CenteredLocation);
              }
-            else if(MouseIsDown && ItemClickedOn == null) //Dragging an empty area
+            else if (MouseIsDown && ItemsSelected.Count >0) //dragging multiple items around
+            {
+                //Track the difference between the last redraw and this re-draw
+                //Move every item by that amount.
+                int xdif = CenteredLocation.X - OrigClickPoint.X ;
+                int ydif = CenteredLocation.Y - OrigClickPoint.Y;
+                if (xdif != 0 || ydif != 0)
+                {
+                    foreach (NetworkDevice nd in ItemsSelected)
+                    {
+                        Point oPoint = nd.myLocation();
+                        Point nPoint = new Point(oPoint.X + xdif, oPoint.Y + ydif);
+                        DragItemToNewLocation(nd, nPoint);
+                    }
+                }
+                //Now set the location so we do it from here next time
+                OrigClickPoint = CenteredLocation;
+            }
+            else if (MouseIsDown && ItemClickedOn == null) //Dragging an empty area
             {
                 //make a rectangle
                 Image tImage = new Bitmap(pbNetworkView.BackgroundImage.Width, pbNetworkView.BackgroundImage.Height);
diff --git a/EduNetworkBuilder/NetworkDevice.cs b/EduNetworkBuilder/NetworkDevice.cs
index fb76802..5b96e87 100644
--- a/EduNetworkBuilder/NetworkDevice.cs
+++ b/EduNetworkBuilder/NetworkDevice.cs
@@ -706,6 +706,11 @@ namespace EduNetworkBuilder
             MyLocation = NB.GetSnapped(Location);
             IsDirty = true;
         }
+        public void ChangeLocationUnsnapped(Point Location)
+        {
+            MyLocation = Location;
+            IsDirty = true;
+        }
 
         public void SetSize(int tSize)
         {