这是找到的画箭头过程,我想按下按钮在IMAGE上才能随意画带箭头的线之后的怎么解决?谢谢
procedure drawArrow(acanvas: tcanvas;ptstart:tpoint;ptend:tpoint;arrowlen:real);
var xa, ya,xb, yb: real;
d: real;
x1, y1, x0, y0: integer;
begin//画直线
acanvas.moveto(ptstart.x, ptstart.y);
acanvas.lineto(ptend.x, ptend.y);
//画箭头
x0 := ptstart.X;
//ptstart是箭头的起点,ptend是终点,都是tpoint型
y0 := ptstart.y;
x1 := ptend.x;
y1 := ptend.y;
d := sqrt((y1 - y0) * (y1 - y0) + (x1 - x0) * (x1 - x0));
if d > 0 then
begin
xa := x1 + arrowlen * ((x0 - x1) + (y0 - y1) / 2) / d;ya := y1 + arrowlen * ((y0 - y1) - (x0 - x1) / 2) / d;
xb := x1 + arrowlen * ((x0 - x1) - (y0 - y1) / 2) / d;
yb := y1 + arrowlen * ((y0 - y1) + (x0 - x1) / 2) / d;
acanvas.moveto(ptend.x, ptend.y);
acanvas.lineto(trunc(xa), trunc(ya));
acanvas.moveto(ptend.x, ptend.y);acanvas.lineto(trunc(xb), trunc(yb));
end;
end;
procedure drawArrow(acanvas: tcanvas;ptstart:tpoint;ptend:tpoint;arrowlen:real);
var xa, ya,xb, yb: real;
d: real;
x1, y1, x0, y0: integer;
begin//画直线
acanvas.moveto(ptstart.x, ptstart.y);
acanvas.lineto(ptend.x, ptend.y);
//画箭头
x0 := ptstart.X;
//ptstart是箭头的起点,ptend是终点,都是tpoint型
y0 := ptstart.y;
x1 := ptend.x;
y1 := ptend.y;
d := sqrt((y1 - y0) * (y1 - y0) + (x1 - x0) * (x1 - x0));
if d > 0 then
begin
xa := x1 + arrowlen * ((x0 - x1) + (y0 - y1) / 2) / d;ya := y1 + arrowlen * ((y0 - y1) - (x0 - x1) / 2) / d;
xb := x1 + arrowlen * ((x0 - x1) - (y0 - y1) / 2) / d;
yb := y1 + arrowlen * ((y0 - y1) + (x0 - x1) / 2) / d;
acanvas.moveto(ptend.x, ptend.y);
acanvas.lineto(trunc(xa), trunc(ya));
acanvas.moveto(ptend.x, ptend.y);acanvas.lineto(trunc(xb), trunc(yb));
end;
end;
随意画带箭头??
========
drawArrow(acanvas: tcanvas;ptstart:tpoint;ptend:tpoint;arrowlen:real);
参数 ptstart,ptend 随即指定 不就可以了???
begin
drawArrow(Form1.Canvas,Point(Round(Random(Self.ClientWidth)),Round(Random(Self.ClientHeight))),
Point(Round(Random(Self.ClientWidth)),Round(Random(Self.ClientHeight))),10);
end;
ss: TCanvas;procedure TForm1.Image1MouseDown(Sender: TObject; Button: TMouseButton;
Shift: TShiftState; X, Y: Integer); begin
GetCursorPos(Pstart);//
end;procedure TForm1.Image1MouseUp(Sender: TObject; Button: TMouseButton;
Shift: TShiftState; X, Y: Integer);
var ss: TCanvas; begin
GetCursorPos(Pend);
ss.Create;
// ss.Brush.Style:= bsSolid;
drawArrow(ss,pstart,pend,1);
ss.Free;
end;
//#include "stdafx.h"
#include "DrawMain.h"#include "DrawMainDoc.h"
#include "DrawMainView.h"
#include <MATH.H>
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endifconst double PI=3.1415926;
const int ArrDgr=30;
const int LineLen=30;
/////////////////////////////////////////////////////////////////////////////
// CDrawMainViewIMPLEMENT_DYNCREATE(CDrawMainView, CView)BEGIN_MESSAGE_MAP(CDrawMainView, CView)
//{{AFX_MSG_MAP(CDrawMainView)
ON_WM_CREATE()
ON_WM_LBUTTONDOWN()
ON_WM_LBUTTONUP()
ON_WM_MOUSEMOVE()
ON_WM_RBUTTONDOWN()
//}}AFX_MSG_MAP
// Standard printing commands
ON_COMMAND(ID_FILE_PRINT, CView::OnFilePrint)
ON_COMMAND(ID_FILE_PRINT_DIRECT, CView::OnFilePrint)
ON_COMMAND(ID_FILE_PRINT_PREVIEW, CView::OnFilePrintPreview)
END_MESSAGE_MAP()/////////////////////////////////////////////////////////////////////////////
// CDrawMainView construction/destructionCDrawMainView::CDrawMainView()
{
// TODO: add construction code here
BSign=FALSE;
}CDrawMainView::~CDrawMainView()
{
}BOOL CDrawMainView::PreCreateWindow(CREATESTRUCT& cs)
{
// TODO: Modify the Window class or styles here by modifying
// the CREATESTRUCT csreturn CView::PreCreateWindow(cs);
}/////////////////////////////////////////////////////////////////////////////
// CDrawMainView drawingvoid CDrawMainView::OnDraw(CDC* pDC)
{
CDrawMainDoc* pDoc = GetDocument();
ASSERT_VALID(pDoc);
// TODO: add draw code for native data here
}/////////////////////////////////////////////////////////////////////////////
// CDrawMainView printingBOOL CDrawMainView::OnPreparePrinting(CPrintInfo* pInfo)
{
// default preparation
return DoPreparePrinting(pInfo);
}void CDrawMainView::OnBeginPrinting(CDC* /*pDC*/, CPrintInfo* /*pInfo*/)
{
// TODO: add extra initialization before printing
}void CDrawMainView::OnEndPrinting(CDC* /*pDC*/, CPrintInfo* /*pInfo*/)
{
// TODO: add cleanup after printing
}/////////////////////////////////////////////////////////////////////////////
// CDrawMainView diagnostics#ifdef _DEBUG
void CDrawMainView::AssertValid() const
{
CView::AssertValid();
}void CDrawMainView::Dump(CDumpContext& dc) const
{
CView::Dump(dc);
}CDrawMainDoc* CDrawMainView::GetDocument() // non-debug version is inline
{
ASSERT(m_pDocument->IsKindOf(RUNTIME_CLASS(CDrawMainDoc)));
return (CDrawMainDoc*)m_pDocument;
}
#endif //_DEBUG/////////////////////////////////////////////////////////////////////////////
// CDrawMainView message handlersint CDrawMainView::OnCreate(LPCREATESTRUCT lpCreateStruct)
{
if (CView::OnCreate(lpCreateStruct) == -1)
return -1;
// TODO: Add your specialized creation code here
m_OrgPot.x=0;
m_OrgPot.y=0;
return 0;
}
void CDrawMainView::OnLButtonDown(UINT nFlags, CPoint point)
{
// TODO: Add your message handler code here and/or call default
m_OrgPot=point;
m_OldPot=point;
BSign=TRUE;
CView::OnLButtonDown(nFlags, point);
}
{
// TODO: Add your message handler code here and/or call default
/*CDC *dc;
dc=GetDC();
dc->MoveTo(m_OrgPot);
dc->LineTo(point);
ReleaseDC(dc);*/
//CClientDC dc(this);
//dc.MoveTo(m_OrgPot);
//dc.LineTo(point);
BSign=FALSE;
CView::OnLButtonUp(nFlags, point);
}void CDrawMainView::OnMouseMove(UINT nFlags, CPoint point)
{
// TODO: Add your message handler code here and/or call default
if (BSign)
{
CClientDC dc(this);
dc.SetROP2(R2_NOTXORPEN);
CPen pen(PS_SOLID,4,RGB(0,255,0));
dc.SelectObject(&pen);
dc.MoveTo(m_OrgPot);
dc.LineTo(m_OldPot);
double x,y,degree;
CPoint ptL,ptR;
if (m_OrgPot.x<=m_OldPot.x)
{
if (m_OrgPot.y<=m_OldPot.y)
{
x=double(m_OldPot.x-m_OrgPot.x);
y=double(m_OldPot.y-m_OrgPot.y);
degree=atan(y/x)+(ArrDgr*PI/180);
ptR.x=m_OldPot.x-int(LineLen*cos(degree)+0.5);
ptR.y=m_OldPot.y-int(LineLen*sin(degree)+0.5);
dc.MoveTo(m_OldPot);
dc.LineTo(ptR);
degree=atan(y/x)-(ArrDgr*PI/180);
ptL.x=m_OldPot.x-int(LineLen*cos(degree)+0.5);
ptL.y=m_OldPot.y-int(LineLen*sin(degree)+0.5);
dc.MoveTo(m_OldPot);
dc.LineTo(ptL);
}
else
{
x=double(m_OldPot.x-m_OrgPot.x);
y=double(m_OrgPot.y-m_OldPot.y);
degree=atan(y/x)+(ArrDgr*PI/180);
ptR.x=m_OldPot.x-int(LineLen*cos(degree)+0.5);
ptR.y=m_OldPot.y+int(LineLen*sin(degree)+0.5);
dc.MoveTo(m_OldPot);
dc.LineTo(ptR);
degree=atan(y/x)-(ArrDgr*PI/180);
ptL.x=m_OldPot.x-int(LineLen*cos(degree)+0.5);
ptL.y=m_OldPot.y+int(LineLen*sin(degree)+0.5);
dc.MoveTo(m_OldPot);
dc.LineTo(ptL);
}
}
else
{
if (m_OrgPot.y<=m_OldPot.y)
{
x=double(m_OrgPot.x-m_OldPot.x);
y=double(m_OldPot.y-m_OrgPot.y);
degree=atan(y/x)-(ArrDgr*PI/180);
ptR.x=m_OldPot.x+int(LineLen*cos(degree)+0.5);
ptR.y=m_OldPot.y-int(LineLen*sin(degree)+0.5);
dc.MoveTo(m_OldPot);
dc.LineTo(ptR);
degree=atan(y/x)+(ArrDgr*PI/180);
ptL.x=m_OldPot.x+int(LineLen*cos(degree)+0.5);
ptL.y=m_OldPot.y-int(LineLen*sin(degree)+0.5);
dc.MoveTo(m_OldPot);
dc.LineTo(ptL);
}
else
{
x=double(m_OrgPot.x-m_OldPot.x);
y=double(m_OrgPot.y-m_OldPot.y);
degree=atan(y/x)-(ArrDgr*PI/180);
ptR.x=m_OldPot.x+int(LineLen*cos(degree)+0.5);
ptR.y=m_OldPot.y+int(LineLen*sin(degree)+0.5);
dc.MoveTo(m_OldPot);
dc.LineTo(ptR);
degree=atan(y/x)+(ArrDgr*PI/180);
ptL.x=m_OldPot.x+int(LineLen*cos(degree)+0.5);
ptL.y=m_OldPot.y+int(LineLen*sin(degree)+0.5);
dc.MoveTo(m_OldPot);
dc.LineTo(ptL);
}
}
dc.MoveTo(m_OrgPot);
dc.LineTo(point);
if (m_OrgPot.x<=point.x)
{
if (m_OrgPot.y<=point.y)
{
x=double(point.x-m_OrgPot.x);
y=double(point.y-m_OrgPot.y);
degree=atan(y/x)+(ArrDgr*PI/180);
ptR.x=point.x-int(LineLen*cos(degree)+0.5);
ptR.y=point.y-int(LineLen*sin(degree)+0.5);
dc.MoveTo(point);
dc.LineTo(ptR);
degree=atan(y/x)-(ArrDgr*PI/180);
ptL.x=point.x-int(LineLen*cos(degree)+0.5);
ptL.y=point.y-int(LineLen*sin(degree)+0.5);
dc.MoveTo(point);
dc.LineTo(ptL);}
else
{
x=double(point.x-m_OrgPot.x);
y=double(m_OrgPot.y-point.y);
degree=(ArrDgr*PI/180)+atan(y/x);
ptR.x=point.x-int(LineLen*cos(degree)+0.5);
ptR.y=point.y+int(LineLen*sin(degree)+0.5);
dc.MoveTo(point);
dc.LineTo(ptR);
degree=atan(y/x)-(ArrDgr*PI/180);
ptL.x=point.x-int(LineLen*cos(degree)+0.5);
ptL.y=point.y+int(LineLen*sin(degree)+0.5);
dc.MoveTo(point);
dc.LineTo(ptL);
}
}
else
{
if (m_OrgPot.y<=point.y)
{
x=double(m_OrgPot.x-point.x);
y=double(point.y-m_OrgPot.y);
degree=atan(y/x)-(ArrDgr*PI/180);
ptR.x=point.x+int(LineLen*cos(degree)+0.5);
ptR.y=point.y-int(LineLen*sin(degree)+0.5);
dc.MoveTo(point);
dc.LineTo(ptR);
degree=atan(y/x)+(ArrDgr*PI/180);
ptL.x=point.x+int(LineLen*cos(degree)+0.5);
ptL.y=point.y-int(LineLen*sin(degree)+0.5);
dc.MoveTo(point);
dc.LineTo(ptL);
}
else
{
x=double(m_OrgPot.x-point.x);
y=double(m_OrgPot.y-point.y);
degree=atan(y/x)-(ArrDgr*PI/180);
ptR.x=point.x+int(LineLen*cos(degree)+0.5);
ptR.y=point.y+int(LineLen*sin(degree)+0.5);
dc.MoveTo(point);
dc.LineTo(ptR);
degree=atan(y/x)+(ArrDgr*PI/180);
ptL.x=point.x+int(LineLen*cos(degree)+0.5);
ptL.y=point.y+int(LineLen*sin(degree)+0.5);
dc.MoveTo(point);
dc.LineTo(ptL);
}
}
m_OldPot=point;
}
CView::OnMouseMove(nFlags, point);
}void CDrawMainView::OnRButtonDown(UINT nFlags, CPoint point)
{
// TODO: Add your message handler code here and/or call default
}