(добавлена информация о xbox)
для окон В основном вам нужно создать форму и показать ее, затем сохранить ее дескриптор и саму форму.
Используя этот дескриптор, вы можете создать GraphicsDevice.
Затем вы подключаете Application.Idle к своей собственной функции, которая вызывает ваше обновление и рендер.
Например
public class MyGame
{
public Form form;
public GraphicsDevice GraphicsDevice;
public MyGame()
{
form = new Form();
form.ClientSize = new Size(1280, 1024);
form.MainMenuStrip = null;
form.Show();
}
public void Run()
{
PresentationParameters pp = new PresentationParameters();
pp.DeviceWindowHandle = form.Handle;
pp.BackBufferFormat = SurfaceFormat.Color;
pp.BackBufferWidth = 1280;
pp.BackBufferHeight = 1024;
pp.RenderTargetUsage = RenderTargetUsage.DiscardContents;
pp.IsFullScreen = false;
pp.MultiSampleCount = 16;
pp.DepthStencilFormat = DepthFormat.Depth24Stencil8;
GraphicsDevice = new GraphicsDevice(GraphicsAdapter.DefaultAdapter,
GraphicsProfile.HiDef,
pp);
Application.Idle += new EventHandler(Application_Idle);
Application.Run(form);
}
private void Application_Idle(object pSender, EventArgs pEventArgs)
{
Message message;
while (!PeekMessage(out message, IntPtr.Zero, 0, 0, 0))
{
/* Your logic goes here
Custom timing and so on
Update();
Render();
*/
}
}
void Render()
{
GraphicsDevice.Clear(ClearOptions.DepthBuffer | ClearOptions.Target, Color.Black, 1, 0);
//Your logic here.
GraphicsDevice.Present();
}
[StructLayout(LayoutKind.Sequential)]
private struct Message
{
public IntPtr hWnd;
public int msg;
public IntPtr wParam;
public IntPtr lParam;
public uint time;
public Point p;
}
[return: MarshalAs(UnmanagedType.Bool)]
[SuppressUnmanagedCodeSecurity, DllImport("user32.dll", CharSet = CharSet.Auto)]
private static extern bool PeekMessage(out Message msg, IntPtr hWnd, uint
messageFilterMin, uint messageFilterMax, uint flags);
}
РЕДАКТИРОВАТЬ 1
Для xbox вы можете просто разместить собственную пользовательскую функцию запуска с игровым циклом в ограниченном цикле true. Внутри, которая выходит за пределы вершины true, вам, вероятно, придется выполнить инициализацию и проверку графического устройства с IntPtr.Zero в качестве дескриптора
РЕДАКТИРОВАТЬ 2
Я использую что-то вроде этого (получил от http://www.koonsolo.com/news/dewitters-gameloop/)
private long nextGameTick;
private Stopwatch stopwatch;
const int ticksPerSecond = 60;
const int skipTicks = 1000 / ticksPerSecond;
private const int maxSkip = 10;
`constructor
stopwatch = Stopwatch.StartNew();
nextGameTick = stopwatch.ElapsedMilliseconds;
`loop
int loops = 0;
long currentTick = stopwatch.ElapsedMilliseconds;
while ( (ulong)(currentTick - nextGameTick) > skipTicks && loops < maxSkip)
{
Update(16.667f);
nextGameTick += skipTicks;
loops++;
}
PreRender();
Render();
PostRender();
РЕДАКТИРОВАТЬ 3
Создание менеджера контента было немного больше работы, но все еще управляемым. Вам нужно создать класс, который реализует IServiceProvider. Этот класс принимает GraphicsDevice в своем конструкторе, чтобы создать следующий класс, реализующий IGraphicsDeviceProvider. кроме того, я реализую GetService, как это
//in implementer of IServiceProvider
public object GetService ( Type serviceType )
{
if ( serviceType == typeof ( IGraphicsDeviceService ) )
{
return myGraphicsService;
}
return null;
}
Для удобства я также добавляю метод в класс для создания и возврата менеджеров
//in implementer of IServiceProvider
public ContentManager CreateContentManager( string sPath )
{
ContentManager content = new ContentManager(this);
content.RootDirectory = sPath;
return content;
}
Кроме того, я создаю класс, который реализует IGraphicsDeviceService и принимает ссылку на мой GraphicsDevice. затем я создаю свойство и поле в нем, например,
//in implementer of IGraphicsDeviceService
private GraphicsDevice graphicsDevice;
public GraphicsDevice GraphicsDevice
{
get
{
return graphicsDevice;
}
}
Таким образом, звонок в конечном итоге выглядит как
MyServiceProvider m = new MyServiceProvider(graphicsDevice);
ContentManager content = m.CreateContentManager("Content");
, где
MyServiceProvider(GraphicsDevice graphicsDevice)
{
myGraphicsService = new MyGraphicsDeviceService(graphicsDevice);
}
MyGraphicsDeviceService(GraphicsDevice gfxDevice)
{
graphicsDevice = gfxDevice;
}
-Извините, что фрагментировал код, но это не то, что я написал слишком недавно, поэтому у меня возникают трудности с запоминанием частей.
РЕДАКТИРОВАТЬ 4
У меня был странный случай с моей пользовательской игрой, которую я только что вспомнил, когда я создал новую форму для нее.
пришлось связать
private void IgnoreAlt(object pSender, KeyEventArgs pEventArgs)
{
if (pEventArgs.Alt && pEventArgs.KeyCode != Keys.F4)
pEventArgs.Handled = true;
}
до
form.KeyUp += IgnoreAlt;
form.KeyDown += IgnoreAlt;
В противном случае у меня есть несколько ужасных киосков.