winform panel绘图问题。
private void InitDraw()
{
//int x = 10, y = 15, dx = 840, dy = 560;
Bitmap bitmap = new Bitmap(this.panel2.ClientSize.Width, this.panel2.ClientSize.Height);
Graphics g = Graphics.FromImage(bitmap);//将绘制内容画到bitmap中。
g.Clear(Color.White);
Pen blackPen = new Pen(Color.Black);//定义一只画笔
SolidBrush redBrush = new SolidBrush(Color.Red);//单色画刷,填充形状
//先画矩形
g.DrawRectangle(blackPen, 10, 15, 840, 560);//以坐标(10,15)为起点画一个宽840,高575的矩形
//画分割线,
for (int i = 0; i < 4; i++)
g.DrawLine(blackPen, 10, 140 * i + 15, 850, 140 * i + 15);//(x,dy/4*i+y,dx+x,dy/4*i+y);
for (int j = 0; j < 4; j++)
{//鼠标单击画线。
//判断鼠标在那个通道上,
if (m_x > 10 && m_y > 140 * j + 15 && m_y < 140 * (j + 1) + 15 && m_x < 850)
{
g.DrawLine(blackPen, m_x, 140 * j + 15, m_x, 140 * (j + 1) + 15);
g.FillEllipse(redBrush, 15, 140 * j + 20, 10, 10);
}
}
for (int k = 0; k < 26;k++ )
{//画底部坐标
if (k % 5 == 0)
g.DrawLine(blackPen, 10 + 33 * k, 568, 10 + 33 * k, 575);
else
g.DrawLine(blackPen, 10 + 33 * k, 572, 10 + 33 * k, 575);
}
//自定义虚线
blackPen.DashPattern = new float[] { 2, 3 };//2表示虚线长度为2px,3表示虚线间隔为3px
for (int i = 0; i < 4; i++)
{
g.DrawLine(blackPen, 10, 140 * i + 85, 850, 140 * i + 85);//(x,dy/4*i+(dy/8+y),dx+x,dy/4*i+(dy/8+y))
}
g.Dispose();
blackPen.Dispose();
redBrush.Dispose();
Graphics gg = this.panel2.CreateGraphics(); //在tabPage1上绘图
gg.DrawImage(bitmap,0,0);//将bitmap图片显示
bitmap.Dispose();
gg.Dispose();
}
//画采集曲线
private void InitDraw_cur()
{
//画采集的曲线
//当前处于哪几个曲线,调文件画曲线
//画采集波形,如果某道有数据就画,没有数据就不画
int i = 0;
byte j ;
for (j = 1; j < 5; j++)
{
if (Trace[j] == true)//首先读通道数组,如果本道有数据,则画曲线
{
short MaxAd = 1;
for (i = 0; i < TPR.SampLen; i++)
{
if (MaxAd < Math.Abs(Tdata[j, i]))
MaxAd = Math.Abs(Tdata[j, i]);
//bufw.Write(Fda[i]);//浮点数
}
//画曲线
int Cu = j - 1;
Graphics g = this.panel2.CreateGraphics();
Pen redPen = new Pen(Color.Red);
double dx = 0, dy0 = 0, dy1 = 0;
dx = (double)840 / TPR.SampLen;
for (i = 0; i < TPR.SampLen - 1; i++)
{
dy0 = (double)Tdata[j, i] / MaxAd;
dy1 = (double)Tdata[j, i + 1] / MaxAd;
g.DrawLine(redPen, 10 + (int)(dx * i), (int)(85 - dy0 * 40) + Cu * 140, 10 + (int)(dx * (i + 1)), (int)(85 - dy1 * 40) + Cu * 140);//46=98/2;中间分割线starX,starY,endX,endY
}
g.Dispose();
redPen.Dispose();
}
}
}
private void panel2_Paint(object sender, PaintEventArgs e)
{
if (FormSty == "采集界面")
{
InitDraw();
InitDraw_cur();
}
else if (FormSty == "单道界面")
{
InitDraw_sign();
InitDraw_singCur();
}
else if (FormSty == "分析界面")
{
InitWave();
InitWave_cur();
}
}
private void panel2_MouseDown(object sender, MouseEventArgs e)
{
if (e.Button == MouseButtons.Left)//单击鼠标左键
{
if (FormSty == "采集界面")
{
m_x = e.X;//获取鼠标点击时x轴坐标
m_y = e.Y;//y坐标
InitDraw();
InitDraw_cur();
}
if (FormSty == "单道界面")
{
m_x = e.X;//获取鼠标点击时x轴坐标
m_y = e.Y;//y坐标
InitDraw_sign();
InitDraw_singCur();
}
}
}
private void panel2_MouseDoubleClick(object sender, MouseEventArgs e)
{
if(FormSty=="单道界面")
{
FormSty = "采集界面";
InitDraw();
InitDraw_cur();
this.单道显示ToolStripMenuItem.Checked = false;
this.多道显示ToolStripMenuItem.Checked = true;
}
else if (FormSty == "采集界面")
{
FormSty = "单道界面";
InitDraw_sign();
InitDraw_singCur();
this.单道显示ToolStripMenuItem.Checked = true;
this.多道显示ToolStripMenuItem.Checked = false;
}
}
private void panel2_MouseMove(object sender, MouseEventArgs e)
{
panel2_MouseDown(sender, e);
}
这样画出来之后,会很闪,本人新手,请大侠分析下代码。 --------------------编程问答-------------------- 设置 Form 的 DoubleBuffer=true;
打开缓冲 --------------------编程问答-------------------- 这样没用的。 --------------------编程问答-------------------- 重载Panel控件,设置双缓冲。
构造函数里写
this.DoubleBuffered = true --------------------编程问答-------------------- Panel.Backgroundimage=.....
设置背景而不是在其上绘图 --------------------编程问答-------------------- 本人新手,不妥之处请拍。
具体代码如下:首先自定义一个PANEL,代替你代码中的PANEL2,当然,接下来在主界面中需要添加之,添加的方法你肯定知道了。。委托,各种事件注册。。
using System;在主界面中的构造函数中可以加入:
using System.Collections.Generic;
using System.Text;
using System.Windows.Forms;
using System.Drawing;
using System.Drawing.Drawing2D;
namespace 你的命名空间
{
public class DrawPanel : Control
{
public DrawPanel()
{
this.DoubleBuffered = true;
this.SetStyle
(
ControlStyles.OptimizedDoubleBuffer |
ControlStyles.ResizeRedraw, true
);
this.Paint += new PaintEventHandler(DrawPanel_Paint);
}
}
//-----------------------DoubleBuffered------------------//
this.SetStyle(
ControlStyles.OptimizedDoubleBuffer |
ControlStyles.ResizeRedraw, true);
this.SetStyle(ControlStyles.DoubleBuffer, true);
this.SetStyle(ControlStyles.UserPaint, true);
this.SetStyle(ControlStyles.AllPaintingInWmPaint, true);
你先尝试下。
--------------------编程问答--------------------
学习,之后我的恶心的代码可以改善下。。全部是在panel上的。 --------------------编程问答-------------------- 一个最简单的方法就是把panel换成pictureBox这个控件就不会闪了
--------------------编程问答-------------------- 双缓冲不是SetStyle(ControlStyles.UserPaint, true);
/// <summary>
/// 重绘事件
/// </summary>
/// <param name="e"></param>
void drawPanel_Paint(object sender, PaintEventArgs e)
{
Bitmap bp = new Bitmap(this.picBoxMain.Width, this.picBoxMain.Height);
//newGraphics = this.panelMain.CreateGraphics();
newGraphics = Graphics.FromImage(bp);
try
{
SetStyle(ControlStyles.UserPaint, true);
SetStyle(ControlStyles.AllPaintingInWmPaint, true); //禁止擦除背景.
SetStyle(ControlStyles.DoubleBuffer, true); // 双缓冲
// 消锯齿(可选项)
newGraphics.SmoothingMode = System.Drawing.Drawing2D.SmoothingMode.AntiAlias;
//高质量
newGraphics.SmoothingMode = SmoothingMode.HighQuality;
for (int i = 0; i < LineManager.ListLine.Count; i++)
{
Line line = LineManager.ListLine[i];
Pen p = new Pen(line.LineColor, line.LineSize);
newGraphics.DrawLine(p, line.StartPoint, line.EndPoint);
}
// 将缓冲位图绘制到输出
e.Graphics.DrawImage(bp, Point.Empty);
}
catch (Exception ex)
{
Console.WriteLine("MainForm-->drawPanel_Paint:" + ex.Message);
}
finally
{
newGraphics.Dispose();
}
}
SetStyle(ControlStyles.AllPaintingInWmPaint, true); //禁止擦除背景.
SetStyle(ControlStyles.DoubleBuffer, true); // 双缓冲
这么几句话设置就完了吧?
this.panel2.CreateGraphics();这样得到Graphics,和e.Graphice。有很大的区别。
--------------------编程问答--------------------
大哥你没看我的回复吗? --------------------编程问答-------------------- 把panel换成pictureBox这个控件就不会闪了 --------------------编程问答--------------------
.你看我代码了? 换成pic一样的效果。
在Panel_Paint里面用e.Graphics得到Graphics绘出来不会闪,
我在自己方法里面只能用this.panel.creartGraphics.得到Graphics。画出来会闪。
Bitmap bitmap = new Bitmap(this.panel2.ClientSize.Width, this.panel2.ClientSize.Height);
Graphics g = Graphics.FromImage(bitmap);这样画出来效果也是不闪的,但加上了曲线就会闪, --------------------编程问答-------------------- --------------------编程问答-------------------- 画了这么多都不会闪 --------------------编程问答--------------------
这样画没有用到双缓冲的效果,所以会闪 --------------------编程问答-------------------- 要用双缓冲才行,要不多次绘制会闪烁。 先把你要画的东西绘制在一个Bitmap上面,然后把这个Bitmap 贴上就就行了。 --------------------编程问答--------------------
就是需要多次绘制,不同的功能绘制不同的效果,都是画在同一个panel上面。
求方案。 --------------------编程问答-------------------- studying --------------------编程问答-------------------- --------------------编程问答-------------------- --------------------编程问答-------------------- http://www.diybl.com/course/4_webprogram/asp.net/netjs/2008520/117339.html
http://www.cnblogs.com/yuanermen/archive/2008/10/09/1307369.html
补充:.NET技术 , C#