You need to find the following:
- Distance to the nearest corner
- Distance to the nearest edge
- (optional) Distance to the center
Basically, you want the smaller of these three values. Take a moment for the two controls to determine which is closer.
Start when you load the form, iterating over all the controls on the form and creating a collection of this class below.
, (. ). , . ContainsPoint(), ... , , ( ). , , , /, .
public class HitControl {
public Control ThisControl;
private Rectangle ControlBounds;
private Point Center;
public HitControl (Control FormControl) {
ControlBounds = FormControl.Bounds;
Center = new Point(ControlBounds.X + (ControlBounds.Width/2), ControlBounds.Y + (ControlBounds.Height/2));
}
public double DistanceFrom(Point TestPoint) {
bool withinWidth = TestPoint.X > ControlBounds.X && TestPoint.X < ControlBounds.X + ControlBounds.Width;
bool withinHeight = TestPoint.Y > ControlBounds.Y && TestPoint.Y < ControlBounds.Y + ControlBounds.Height;
int EdgeLeftXDistance = Math.Abs(ControlBounds.X - TestPoint.X);
int EdgeRightXDistance = Math.Abs(ControlBounds.X + ControlBounds.Width - TestPoint.X);
int EdgeTopYDistance = Math.Abs(ControlBounds.Y - TestPoint.Y);
int EdgeBottomYDistance = Math.Abs(ControlBounds.Y + ControlBounds.Height - TestPoint.Y);
int EdgeXDistance = Math.Min(EdgeLeftXDistance, EdgeRightXDistance);
int EdgeYDistance = Math.Min(EdgeTopYDistance, EdgeBottomYDistance);
if (withinWidth && withinHeight) {
return Math.Min(EdgeXDistance, EdgeYDistance);
}
if (withinWidth) {
return EdgeYDistance;
}
if (withinHeight) {
return EdgeXDistance;
}
return Math.Sqrt(EdgeXDistance ^ 2 + EdgeYDistance ^ 2);
}
public bool ContainsPoint (Point TestPoint) {
return ControlBounds.Contains(TestPoint);
}
}
List<HitControl> hitControls = (from Control control in Controls
select new HitControl(control)).ToList();
Point testPoint = new Point(175, 619);
double distance;
double shortestDistance = 0;
HitControl closestControl = null;
foreach (HitControl hitControl in hitControls) {
if (hitControl.ContainsPoint(testPoint)) {
closestControl = hitControl;
break;
}
distance = hitControl.DistanceFrom(testPoint);
if (shortestDistance == 0 || distance < shortestDistance) {
shortestDistance = distance;
closestControl = hitControl;
}
}
if (closestControl != null) {
Control foundControl = closestControl.ThisControl;
}