Original Post
I am working on an application in C# .NET. In the application we need to be able to graph data being received as fast as possible. I've been looking into different technologies to determine the most efficient way to draw the graphs which are simply a connected series of lines. I was experimenting with Direct2d and using SharpDX (or SlimDX) to integrate the DirectX into my application. However, it does not seem as if the line drawing code that I am experimenting with is being hardware accelerated. I am only getting around 25 frames per second, drawing a few hundred lines on a panel in the .NET application using Direct2d. Also, the GDI code I wrote renders the lines about 4 times faster than the direct2d calls.
Here's what I've tried to render the lines.. in the most basic way. Is this being hardware accelerated? (I have 2 cards, one is much better than the other, both render same amount of times and hit the CPU hard) I feel like I should get more than 25 frames per second on a panel that is less than 1000 pixels wide (in this example less than 1000 lines)
Here's what I've tried to render the lines.. in the most basic way. Is this being hardware accelerated? (I have 2 cards, one is much better than the other, both render same amount of times and hit the CPU hard) I feel like I should get more than 25 frames per second on a panel that is less than 1000 pixels wide (in this example less than 1000 lines)
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using SharpDX.Direct2D1;
using SharpDX.DXGI;
using System.Diagnostics;
using SharpDX.Direct3D10;
using Device = SharpDX.Direct3D10.Device;
using Device1 = SharpDX.Direct3D10.Device1;
using DriverType = SharpDX.Direct3D10.DriverType;
using FeatureLevel = SharpDX.Direct3D10.FeatureLevel;
using Factory = SharpDX.Direct2D1.Factory;
using SharpDX;
namespace GraphDrawingTests
{
public partial class GraphDrawingDialog : Form
{
PointF[][] pts;
Factory factory;
WindowRenderTarget renderTarget;
Device1 device;
SwapChain swapChain;
Texture2D backBuffer;
RenderTargetView backBufferView;
public GraphDrawingDialog()
{
InitializeComponent();
Random r = new Random();
pts = new PointF[10][];
for (int i = 0; i < pts.Length; i++)
{
pts = new PointF[panel1.Width];
for (int k = 0; k < pts.Length; k++)
{
pts[k] = new PointF(k, r.Next(0, panel1.Height));
}
}
/*
* Confused on why I woul dneed to do this?
*
* SwapChainDescription desc = new SwapChainDescription()
{
BufferCount = 1,
ModeDescription =
new ModeDescription(panel1.Width, panel1.Height,
new Rational(60, 1), Format.R8G8B8A8_UNorm),
IsWindowed = true,
OutputHandle = panel1.Handle,
SampleDescription = new SampleDescription(1, 0),
SwapEffect = SwapEffect.Discard,
Usage = Usage.RenderTargetOutput
};
SharpDX.Direct3D10.Device1.CreateWithSwapChain(DriverType.Hardware,
DeviceCreationFlags.Debug | DeviceCreationFlags.BgraSupport,
desc,
SharpDX.Direct3D10.FeatureLevel.Level_10_0,
out device,
out swapChain);
factory = swapChain.GetParent<Factory>();
factory.MakeWindowAssociation(panel1.Handle, WindowAssociationFlags.IgnoreAll);
backBuffer = Texture2D.FromSwapChain<Texture2D>(swapChain, 0);
backBufferView = new RenderTargetView(device, backBuffer);
*/
factory = new SharpDX.Direct2D1.Factory(FactoryType.SingleThreaded);
renderTarget = new WindowRenderTarget(
factory,
new RenderTargetProperties(),
new HwndRenderTargetProperties()
{
Hwnd = panel1.Handle,
PixelSize = new System.Drawing.Size(panel1.Width, panel1.Height)
});
}
protected override void OnClosed(EventArgs e)
{
renderTarget.Dispose();
factory.Dispose();
base.OnClosed(e);
}
private void button1_Click(object sender, EventArgs e)
{
Stopwatch sw = new Stopwatch();
sw.Start();
int frames = 0;
while (sw.ElapsedMilliseconds < 2000)
{
PathGeometry geometry = new PathGeometry(factory);
GeometrySink sink = geometry.Open();
sink.BeginFigure(new PointF(0, 0), new FigureBegin());
sink.AddLines(pts[frames % 10]);
sink.EndFigure(new FigureEnd());
sink.Close();
renderTarget.BeginDraw();
renderTarget.Clear(new SharpDX.Color4(255, 0, 0, 0));
SolidColorBrush brush = new SolidColorBrush(renderTarget, new SharpDX.Color4(255, 255, 255, 255));
renderTarget.DrawGeometry(geometry, brush);
brush.Dispose();
renderTarget.EndDraw();
geometry.Dispose();
frames++;
}
MessageBox.Show("D2D Frames: " + frames);
}
private void button2_Click(object sender, EventArgs e)
{
Stopwatch sw = new Stopwatch();
sw.Start();
int frames = 0;
while (sw.ElapsedMilliseconds < 2000)
{
Graphics gfx = panel1.CreateGraphics();
gfx.Clear(Color.Black);
Pen p = new Pen(Color.White);
gfx.DrawLines(p, pts[frames % 10]);
p.Dispose();
gfx.Dispose();
frames++;
}
MessageBox.Show("GDI Frames: " + frames);
}
}
}