跪求GDI+画图框选问题解决方案

cshu5302930 2010-05-24 06:19:33
本人使用GDI+画了个折线,现在需要拉框选择。不知道如何判断拉框的矩形和已画的折线是否相交或者包含,请各位大虾帮忙,谢谢!
...全文
184 12 打赏 收藏 转发到动态 举报
写回复
用AI写文章
12 条回复
切换为时间正序
请发表友善的回复…
发表回复
shighui 2010-05-26
  • 打赏
  • 举报
回复
[Quote=引用 3 楼 skep99 的回复:]
引用 2 楼 cshu5302930 的回复:
谢谢你的回答,这样判断不准确,如果我只拉框个很小矩形选择这条折线中的一小段,就没法判断了。


看来没看明白,
画线的时候记录上下左右的最大最小值,也就是折线的外接矩形,
然后和后画的框的四个顶点分别作判断

道理是如此,gdi的IntersectsWith方法已经实现
例子:

C# code

priva……
[/Quote]sdf
cshu5302930 2010-05-26
  • 打赏
  • 举报
回复
谢谢pzy1234567,谢谢各位,pzy1234567的代码只判断了矩形的顶点是否在这条线段上取到y值,所以还有所欠缺。我也看了一个矢量绘图软件的源代码,他的思路和各位思路一样,判断矩形各个边和线段是否有交点,这样问题就转化为求2个线段是否相交的问题了。如果哪位有类似代码请分享下。谢谢!
cshu5302930 2010-05-25
  • 打赏
  • 举报
回复
谢谢你的回答,这样判断不准确,如果我只拉框个很小矩形选择这条折线中的一小段,就没法判断了。
sxldfang 2010-05-25
  • 打赏
  • 举报
回复
如果没有现成的类,只能自己写啦!显然楼主是在问有无现成的类吧
pzy1234567 2010-05-25
  • 打赏
  • 举报
回复
刚写了一个类,可以实现楼主所说的判断,贴出来看一下,经过简单的测试,是正确的,如果有错误,修改下应该就可以,整体思路应该是正确的。
使用非常简单,只要使用两个点,线段的起点和终点来构造类对象,然后调用IntersectOrContain方法,参数是判断是否相交的矩形,返回bool值来标示是否相交或包含
public class Line
{
//y = kX + b
//k=(y2-y1)/(x2-x1)
private Point p1;
private Point p2;
private double? k = 0;
private double b;
private Line()
{
}
public Line(Point p1, Point p2)
{
if (p1 == p2)
{
p2.X = p1.X + 1;
}
this.p1 = p1;
this.p2 = p2;

try
{
this.k = (double)(p2.Y - p1.Y) / (double)(p2.X - p1.X);
}
catch (DivideByZeroException e)
{
this.k = null;
b = p1.X;
}

if (k.HasValue)
{
b = (double)p1.Y - k.Value * (double)p1.X;
}
}

/// <summary>
/// judge the rect intersect or contain this line
/// </summary>
/// <param name="rect"></param>
/// <returns>if true, it indicates the rect contain or intersect this line, otherwise false.</returns>
public bool IntersectOrContain(Rectangle rect)
{
if (rect.Left < MinX &&
rect.Right > MaxX &&
rect.Top < MinY &&
rect.Bottom > MaxY)
{
//contain the line
return true;
}

//judge whether the line intersect the left border of rect
int? y = GetYValue(rect.Left);
if (y.HasValue)
{
if(y >= rect.Top && y <= rect.Bottom)
return true;
}

//judge whether the line intersect the right border of rect
y = GetYValue(rect.Right);
if (y.HasValue)
{
if (y >= rect.Top && y <= rect.Bottom)
return true;
}

//judge whter the line intersect the top border of rect
int? x = GetXValue(rect.Top);
if (x.HasValue)
{
if(x >= rect.Left && x <= rect.Right)
return true;
}
//judge whter the line intersect the bottom border of rect
x = GetXValue(rect.Bottom);
if (x.HasValue)
{
if (x >= rect.Left && x <= rect.Right)
return true;
}
return false;
}

/// <summary>
/// Get the Y value using x value.
/// </summary>
/// <param name="x"></param>
/// <returns>if null, it indicates the value can not be calculate.</returns>
public int? GetYValue(int x)
{
if (k.HasValue)
{
int y = (int)(k.Value * x + b);
if (y >= MinY && y <= MaxY)
{
return y;
}
else
{
return null;
}
}
else
{
return null;
}
}

/// <summary>
/// Get the X value using y value.
/// </summary>
/// <param name="y"></param>
/// <returns>if null, it indicates the value can not be calculate.</returns>
public int? GetXValue(int y)
{
if (k.HasValue)
{
try
{
int x = (int)(((double)y - b) / k);
if (x >= MinX && x <= MaxX)
{
return x;
}
else
{
return null;
}
}
catch (DivideByZeroException e)
{
return null;
}
}
else
{
return p1.X;
}
}
/// <summary>
/// if k is null, it indicates the k is endless
/// </summary>
public double? K
{
get
{
return this.k;
}
}
/// <summary>
/// the b value
/// </summary>
public double B
{
get
{
return this.b;
}
}
/// <summary>
/// the min value of X
/// </summary>
public int MinX
{
get
{
return Math.Min(p1.X, p2.X);
}
}
/// <summary>
/// the max value of X
/// </summary>
public int MaxX
{
get
{
return Math.Max(p1.X, p2.X);
}
}
/// <summary>
/// the min value of Y
/// </summary>
public int MinY
{
get
{
return Math.Min(p1.Y, p2.Y);
}
}
/// <summary>
/// the max value of Y
/// </summary>
public int MaxY
{
get
{
return Math.Max(p1.Y, p2.Y);
}
}
}
xmdxcxz 2010-05-25
  • 打赏
  • 举报
回复
不懂,帮你顶了
skep99 2010-05-25
  • 打赏
  • 举报
回复
[Quote=引用 4 楼 cshu5302930 的回复:]
谢谢你的回答,你此方法是判断2个矩形是否相交,我说的是矩形和折线。用折线的外接矩形判断不准确。
[/Quote]

之前我理解有问题
先判断每段折线所在矩形是否与左侧矩形相交
如果相交再判断该段折线是否与左侧矩形的两条对角线的任意一条是否有交点
softman11 2010-05-25
  • 打赏
  • 举报
回复
[Quote=引用 4 楼 cshu5302930 的回复:]
谢谢你的回答,你此方法是判断2个矩形是否相交,我说的是矩形和折线。用折线的外接矩形判断不准确。
[/Quote]

转成判断直线是否和矩形有交点。
因为你折现是由若干线段构成的。

判断直线和矩形相交,这个简单了吧。
ATGO 2010-05-25
  • 打赏
  • 举报
回复
我也处理过类似的问题,数学问题用向量很好地解决了。
cshu5302930 2010-05-25
  • 打赏
  • 举报
回复
谢谢你的回答,你此方法是判断2个矩形是否相交,我说的是矩形和折线。用折线的外接矩形判断不准确。
skep99 2010-05-25
  • 打赏
  • 举报
回复
[Quote=引用 2 楼 cshu5302930 的回复:]
谢谢你的回答,这样判断不准确,如果我只拉框个很小矩形选择这条折线中的一小段,就没法判断了。
[/Quote]

看来没看明白,
画线的时候记录上下左右的最大最小值,也就是折线的外接矩形,
然后和后画的框的四个顶点分别作判断

道理是如此,gdi的IntersectsWith方法已经实现
例子:

private void InstanceRectangleIntersection(PaintEventArgs e)
{

Rectangle rectangle1 = new Rectangle(50, 50, 200, 100);
Rectangle rectangle2 = new Rectangle(70, 20, 100, 200);

e.Graphics.DrawRectangle(Pens.Black, rectangle1);
e.Graphics.DrawRectangle(Pens.Red, rectangle2);

if (rectangle1.IntersectsWith(rectangle2))
{
rectangle1.Intersect(rectangle2);
if (!rectangle1.IsEmpty)
{
e.Graphics.FillRectangle(Brushes.Red, rectangle1);
}
}
}
skep99 2010-05-24
  • 打赏
  • 举报
回复
判断矩形左上角和右下角两个坐标是否分别大于折线左右上下极值

110,534

社区成员

发帖
与我相关
我的任务
社区描述
.NET技术 C#
社区管理员
  • C#
  • Web++
  • by_封爱
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

让您成为最强悍的C#开发者

试试用AI创作助手写篇文章吧