在51aspx上找到一个非常酷的画几何图形的源码。可惜太复杂,看不懂。
干脆自己琢磨吧,先动态画条直线,画个圆,所谓动态就是指画直线或圆的时候,能显示中间过程。
同时学到了怎样计算两个点之间的距离,怎样画虚线。
大气象
<
UserControl
x:Class
="DrawLine.DrawEclipse"
xmlns ="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x ="http://schemas.microsoft.com/winfx/2006/xaml"
Width ="400" Height ="300" >
< Canvas x:Name ="panel" Background ="Black" MouseMove ="panel_MouseMove" MouseLeftButtonDown ="panel_MouseLeftButtonDown" >
</ Canvas >
</ UserControl >
xmlns ="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x ="http://schemas.microsoft.com/winfx/2006/xaml"
Width ="400" Height ="300" >
< Canvas x:Name ="panel" Background ="Black" MouseMove ="panel_MouseMove" MouseLeftButtonDown ="panel_MouseLeftButtonDown" >
</ Canvas >
</ UserControl >
大气象
using
System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;
namespace DrawLine
{
public partial class DrawEclipse : UserControl
{
public DrawEclipse()
{
InitializeComponent();
}
private bool IsStart = true ; // 是否是起点。
private double pX1 = 0 , pY1 = 0 ; // 起点坐标
private double pX2 = 0 , pY2 = 0 ; // 终点坐标
Ellipse ellipse = new Ellipse(); // 画圆心
Ellipse ellipseTmp = new Ellipse(); // 画临时圆
Line lineTmp = new Line(); // 临时直线
private void panel_MouseLeftButtonDown( object sender, MouseButtonEventArgs e)
{
Point p = e.GetPosition(sender as FrameworkElement); // 取得鼠标点下的位置
Canvas pnl = sender as Canvas;
if (IsStart)
{
pX1 = p.X; // 设置起点坐标
pY1 = p.Y;
}
else
{
pX2 = p.X; // 设置终点坐标
pY2 = p.Y;
}
if (IsStart) // 如果是起点,则画起点。
{
DrawPoint(pnl);
}
else
{
DrawOneEclipse(pnl);
if (lineTmp != null )
pnl.Children.Remove(lineTmp);
}
IsStart = ! IsStart;
}
// 画圆
private void DrawOneEclipse(Canvas pnl)
{
Ellipse ellipseOne = new Ellipse(); // 画圆
ellipseOne.Stroke = new SolidColorBrush(Color.FromArgb( 255 , 255 , 255 , 255 )); // 动态设置Stroke属性的方法。
ellipseOne.StrokeThickness = 2 ;
// 计算两点距离
Point p1 = new Point(pX1, pY1);
Point p2 = new Point(pX2, pY2);
//
var dx = p1.X - p2.X;
var dy = p1.Y - p2.Y;
double distance = Math.Sqrt(dx * dx + dy * dy);
ellipseOne.Width = distance * 2 ;
ellipseOne.Height = distance * 2 ;
Canvas.SetLeft(ellipseOne, pX1 - distance); // 动态设置Ellipse的Canvas.Top与Canvas.Left
Canvas.SetTop(ellipseOne, pY1 - distance);
pnl.Children.Add(ellipseOne);
}
// 画点
private void DrawPoint(Canvas pnl)
{
ellipse.Stroke = new SolidColorBrush(Color.FromArgb( 255 , 255 , 255 , 255 )); // 动态设置Stroke属性的方法。
ellipse.StrokeThickness = 2 ;
ellipse.Width = 4 ;
ellipse.Height = 4 ;
Canvas.SetLeft(ellipse, pX1); // 动态设置Ellipse的Canvas.Top与Canvas.Left
Canvas.SetTop(ellipse, pY1);
pnl.Children.Add(ellipse);
}
// 画临时圆
private void DrawTmpEclipse(Canvas pnl)
{
if (ellipseTmp != null )
pnl.Children.Remove(ellipseTmp);
ellipseTmp.Stroke = new SolidColorBrush(Color.FromArgb( 255 , 255 , 255 , 255 )); // 动态设置Stroke属性的方法。
ellipseTmp.StrokeThickness = 2 ;
// 计算两点距离
Point p1 = new Point(pX1, pY1);
Point p2 = new Point(pX2, pY2);
//
var dx = p1.X - p2.X;
var dy = p1.Y - p2.Y;
double distance = Math.Sqrt(dx * dx + dy * dy);
ellipseTmp.Width = distance * 2 ;
ellipseTmp.Height = distance * 2 ;
Canvas.SetLeft(ellipseTmp, pX1 - distance); // 动态设置Ellipse的Canvas.Top与Canvas.Left
Canvas.SetTop(ellipseTmp, pY1 - distance);
pnl.Children.Add(ellipseTmp);
pnl.Children.Remove(ellipse); // 删除起点。
}
// 画临时直线
private void DrawTmpLine(Canvas pnl)
{
if (lineTmp != null )
pnl.Children.Remove(lineTmp);
lineTmp.X1 = pX1;
lineTmp.Y1 = pY1;
lineTmp.X2 = pX2;
lineTmp.Y2 = pY2;
lineTmp.Stroke = new SolidColorBrush(Color.FromArgb( 255 , 255 , 255 , 255 ));
lineTmp.StrokeThickness = 2 ;
// 设置虚线的方法
DoubleCollection dc = new DoubleCollection(){ 1 , 1 };
lineTmp.StrokeDashArray = dc;
pnl.Children.Add(lineTmp);
}
private void panel_MouseMove( object sender, MouseEventArgs e)
{
Point p = e.GetPosition(sender as FrameworkElement); // 取得鼠标点下的位置
Canvas pnl = sender as Canvas;
if ( ! IsStart) // 如果不是起点,则设置临时终点
{
pX2 = p.X; // 设置终点坐标
pY2 = p.Y;
DrawTmpLine(pnl);
DrawTmpEclipse(pnl);
}
}
}
}
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;
namespace DrawLine
{
public partial class DrawEclipse : UserControl
{
public DrawEclipse()
{
InitializeComponent();
}
private bool IsStart = true ; // 是否是起点。
private double pX1 = 0 , pY1 = 0 ; // 起点坐标
private double pX2 = 0 , pY2 = 0 ; // 终点坐标
Ellipse ellipse = new Ellipse(); // 画圆心
Ellipse ellipseTmp = new Ellipse(); // 画临时圆
Line lineTmp = new Line(); // 临时直线
private void panel_MouseLeftButtonDown( object sender, MouseButtonEventArgs e)
{
Point p = e.GetPosition(sender as FrameworkElement); // 取得鼠标点下的位置
Canvas pnl = sender as Canvas;
if (IsStart)
{
pX1 = p.X; // 设置起点坐标
pY1 = p.Y;
}
else
{
pX2 = p.X; // 设置终点坐标
pY2 = p.Y;
}
if (IsStart) // 如果是起点,则画起点。
{
DrawPoint(pnl);
}
else
{
DrawOneEclipse(pnl);
if (lineTmp != null )
pnl.Children.Remove(lineTmp);
}
IsStart = ! IsStart;
}
// 画圆
private void DrawOneEclipse(Canvas pnl)
{
Ellipse ellipseOne = new Ellipse(); // 画圆
ellipseOne.Stroke = new SolidColorBrush(Color.FromArgb( 255 , 255 , 255 , 255 )); // 动态设置Stroke属性的方法。
ellipseOne.StrokeThickness = 2 ;
// 计算两点距离
Point p1 = new Point(pX1, pY1);
Point p2 = new Point(pX2, pY2);
//
var dx = p1.X - p2.X;
var dy = p1.Y - p2.Y;
double distance = Math.Sqrt(dx * dx + dy * dy);
ellipseOne.Width = distance * 2 ;
ellipseOne.Height = distance * 2 ;
Canvas.SetLeft(ellipseOne, pX1 - distance); // 动态设置Ellipse的Canvas.Top与Canvas.Left
Canvas.SetTop(ellipseOne, pY1 - distance);
pnl.Children.Add(ellipseOne);
}
// 画点
private void DrawPoint(Canvas pnl)
{
ellipse.Stroke = new SolidColorBrush(Color.FromArgb( 255 , 255 , 255 , 255 )); // 动态设置Stroke属性的方法。
ellipse.StrokeThickness = 2 ;
ellipse.Width = 4 ;
ellipse.Height = 4 ;
Canvas.SetLeft(ellipse, pX1); // 动态设置Ellipse的Canvas.Top与Canvas.Left
Canvas.SetTop(ellipse, pY1);
pnl.Children.Add(ellipse);
}
// 画临时圆
private void DrawTmpEclipse(Canvas pnl)
{
if (ellipseTmp != null )
pnl.Children.Remove(ellipseTmp);
ellipseTmp.Stroke = new SolidColorBrush(Color.FromArgb( 255 , 255 , 255 , 255 )); // 动态设置Stroke属性的方法。
ellipseTmp.StrokeThickness = 2 ;
// 计算两点距离
Point p1 = new Point(pX1, pY1);
Point p2 = new Point(pX2, pY2);
//
var dx = p1.X - p2.X;
var dy = p1.Y - p2.Y;
double distance = Math.Sqrt(dx * dx + dy * dy);
ellipseTmp.Width = distance * 2 ;
ellipseTmp.Height = distance * 2 ;
Canvas.SetLeft(ellipseTmp, pX1 - distance); // 动态设置Ellipse的Canvas.Top与Canvas.Left
Canvas.SetTop(ellipseTmp, pY1 - distance);
pnl.Children.Add(ellipseTmp);
pnl.Children.Remove(ellipse); // 删除起点。
}
// 画临时直线
private void DrawTmpLine(Canvas pnl)
{
if (lineTmp != null )
pnl.Children.Remove(lineTmp);
lineTmp.X1 = pX1;
lineTmp.Y1 = pY1;
lineTmp.X2 = pX2;
lineTmp.Y2 = pY2;
lineTmp.Stroke = new SolidColorBrush(Color.FromArgb( 255 , 255 , 255 , 255 ));
lineTmp.StrokeThickness = 2 ;
// 设置虚线的方法
DoubleCollection dc = new DoubleCollection(){ 1 , 1 };
lineTmp.StrokeDashArray = dc;
pnl.Children.Add(lineTmp);
}
private void panel_MouseMove( object sender, MouseEventArgs e)
{
Point p = e.GetPosition(sender as FrameworkElement); // 取得鼠标点下的位置
Canvas pnl = sender as Canvas;
if ( ! IsStart) // 如果不是起点,则设置临时终点
{
pX2 = p.X; // 设置终点坐标
pY2 = p.Y;
DrawTmpLine(pnl);
DrawTmpEclipse(pnl);
}
}
}
}
本文源码:http://files.cnblogs.com/greatverve/DrawLineEclipse.rar
参考:http://51aspx.com/CV/SLGeometry/
这个源码酷多了。看看吧。