我知道这个问题的术语肯定是错误的,但请多多包涵,试着从我门外汉的角度来看事情(我没有计算机技术的形成,我是一个自学成才的爱好者。我得到的最接近的编程语言的正规教育是我学校的机器人俱乐部)。
我想要的是能够使用托管 DirectX 12 作为我的应用程序的“背景”,以及游戏循环等等。并且,如果可能的话,能够拥有 WPF 控件,如功能区或工具箱或实际 directX 游戏周围的菜单。我一直在寻找整个互联网,我发现的只是 Windows 和 DirectX 9.0 的非常旧的东西;我希望这些天有新的东西。
我尝试了 Windows Form 方法,基本上是这样的:
using System;
using System.Windows;
using System.Windows.Interop;
using Microsoft.DirectX.Direct3D;
using DColor = System.Drawing.Color;
public partial class MainWindow : Window
{
Device device;
public MainWindow()
{
InitializeComponent();
initDevice();
}
private void initDevice()
{
try
{
PresentParameters parameters = new PresentParameters();
parameters.Windowed = true;
parameters.SwapEffect = SwapEffect.Discard;
IntPtr windowHandle = new WindowInteropHelper(this).Handle;
device = new Device(0, DeviceType.Hardware, windowHandle, CreateFlags.HardwareVertexProcessing, parameters);
}
catch(Exception e)
{
MessageBox.Show("initDevice threw an Exception\n" + e.Message, "ERROR", MessageBoxButton.OK, MessageBoxImage.Error);
}
}
private void render()
{
device.Clear(ClearFlags.Target, DColor.LightGreen, 0f, 1);
device.Present();
}
}
不会抛出异常,窗口根本不会呈现。应用程序运行,但窗口不显示。我不认为这会起作用,因为没有游戏循环并且render
不会从任何地方调用,但我没想到窗口甚至没有显示。如果我注释掉调用 initDevice() 的行,WPF 的空白窗口会正常显示
然后我发现该CompositionTarget.Rendering
事件每帧(或滴答声?)被调用一次,因此该事件的处理程序必须用作游戏循环。
所以我尝试了这个:
using System;
using System.Drawing;
using System.IO;
using System.Windows;
using System.Windows.Media;
using System.Windows.Forms.Integration;
using Microsoft.DirectX.Direct3D;
using DColor = System.Drawing.Color;
using System.Windows.Forms;
public partial class MainWindow : Window
{
Device device = null;
MemoryStream stream;
PictureBox display;
WindowsFormsHost host;
public MainWindow()
{
InitializeComponent();
initDevice();
CompositionTarget.Rendering += CompositionTarget_Rendering;
}
private void CompositionTarget_Rendering(object sender, EventArgs e)
{
render();
}
private void initDevice()
{
try
{
PresentParameters parameters = new PresentParameters();
parameters.Windowed = true;
parameters.SwapEffect = SwapEffect.Discard;
device = new Device(0, DeviceType.Hardware, display, CreateFlags.HardwareVertexProcessing, parameters);
stream = new MemoryStream();
device.SetRenderTarget(0, new Surface(device, stream, Pool.Managed));
}
catch(Exception e)
{
System.Windows.MessageBox.Show("initDevice threw an Exception\n" + e.Message, "ERROR", MessageBoxButton.OK, MessageBoxImage.Error);
}
}
private void render()
{
device.Clear(ClearFlags.Target, DColor.LightGreen, 0f, 1);
device.Present();
display.Image = Image.FromStream(stream);
}
private void Window_Loaded(object sender, RoutedEventArgs e)
{
host = new WindowsFormsHost();
display = new PictureBox();
host.Child = display;
mainGrid.Children.Add(host);
}
}
即使应用程序正在运行并且没有崩溃,仍然没有显示窗口。
最后我尝试了同样的事情,但没有处理CompositionTarget.Rendering
,而是使用 DispatcherTimer,并从其Tick
事件处理程序内部调用 render 。结果相同:没有窗口。
谁能指出我正确的方向?