Skip to content

Instantly share code, notes, and snippets.

@aleksas
Last active October 22, 2019 14:51
Show Gist options
  • Select an option

  • Save aleksas/06d6c300d1f01cea5f96cd7b3d8e6a76 to your computer and use it in GitHub Desktop.

Select an option

Save aleksas/06d6c300d1f01cea5f96cd7b3d8e6a76 to your computer and use it in GitHub Desktop.
C# SDL2 Panel control wrapping SDL2 window. Based on this snippet: https://gist.github.com/flibitijibibo/cf282bfccc1eaeb47550.
using SDL2;
using System;
using System.ComponentModel;
using System.Runtime.InteropServices;
using System.Windows.Forms;
namespace DesktopApp1
{
class SDL2Panel : Panel
{
#region WinAPI Entry Points
[DllImport("user32.dll")]
private static extern IntPtr SetWindowPos(
IntPtr handle,
IntPtr handleAfter,
int x,
int y,
int cx,
int cy,
uint flags
);
[DllImport("user32.dll", SetLastError = true)]
public static extern bool MoveWindow(IntPtr hWnd, int X, int Y, int nWidth, int nHeight, bool bRepaint);
[DllImport("user32.dll")]
private static extern IntPtr SetParent(IntPtr child, IntPtr newParent);
[DllImport("user32.dll")]
private static extern IntPtr ShowWindow(IntPtr handle, int command);
#endregion
#region Private Variables
private IntPtr glContext;
private delegate void Viewport(int x, int y, int width, int height);
private delegate void ClearColor(float r, float g, float b, float a);
private delegate void Clear(uint flags);
private Viewport glViewport;
private ClearColor glClearColor;
private Clear glClear;
#endregion
#region Private SDL2 Window/Control Handles
private IntPtr gameWindow;
private IntPtr winHandle;
#endregion
private bool InDesignerMode
{
get
{
return LicenseManager.UsageMode == LicenseUsageMode.Designtime || DesignMode;
}
}
private void InitializeSDLWindow()
{
if (!InDesignerMode)
{
SDL.SDL_Init(SDL.SDL_INIT_VIDEO);
gameWindow = SDL.SDL_CreateWindow(
String.Empty,
0,
0,
Size.Width,
Size.Height,
SDL.SDL_WindowFlags.SDL_WINDOW_BORDERLESS | SDL.SDL_WindowFlags.SDL_WINDOW_OPENGL// | SDL.SDL_WindowFlags.SDL_WINDOW_RESIZABLE
);
glContext = SDL.SDL_GL_CreateContext(gameWindow);
glViewport = (Viewport)Marshal.GetDelegateForFunctionPointer(
SDL.SDL_GL_GetProcAddress("glViewport"),
typeof(Viewport)
);
glClearColor = (ClearColor)Marshal.GetDelegateForFunctionPointer(
SDL.SDL_GL_GetProcAddress("glClearColor"),
typeof(ClearColor)
);
glClear = (Clear)Marshal.GetDelegateForFunctionPointer(
SDL.SDL_GL_GetProcAddress("glClear"),
typeof(Clear)
);
glViewport(0, 0, Size.Width, Size.Height);
glClearColor(1.0f, 0.0f, 0.0f, 1.0f);
glClear(0x4000);
SDL.SDL_GL_SwapWindow(gameWindow);
// Get the Win32 HWND from the SDL2 window
SDL.SDL_SysWMinfo info = new SDL.SDL_SysWMinfo();
SDL.SDL_GetWindowWMInfo(gameWindow, ref info);
winHandle = info.info.win.window;
// Move the SDL2 window to 0, 0
SetWindowPos(
winHandle,
Handle,
0,
0,
0,
0,
0x0401 // NOSIZE | SHOWWINDOW
);
// Attach the SDL2 window to the panel
SetParent(winHandle, Handle);
ShowWindow(winHandle, 1); // SHOWNORMAL
}
}
private void SDL2Panel_Resize1(object sender, EventArgs e)
{
throw new NotImplementedException();
}
public SDL2Panel()
{
HandleDestroyed += SDL2Panel_HandleDestroyed;
Resize += SDL2Panel_Resize;
InitializeSDLWindow();
}
public void ReandomColor()
{
var random = new Random();
glClearColor(
(float)random.NextDouble(),
(float)random.NextDouble(),
(float)random.NextDouble(),
1.0f
);
glClear(0x4000); // GL_COLOR_BUFFER_BIT
SDL.SDL_GL_SwapWindow(gameWindow);
}
private void SDL2Panel_Resize(object sender, EventArgs e)
{
if (!InDesignerMode)
{
SDL.SDL_SetWindowSize(gameWindow, Size.Width, Size.Height);
MoveWindow(winHandle, 0, 0, Size.Width, Size.Height, true);
glViewport(0, 0, Size.Width, Size.Height);
glClear(0x4000); // GL_COLOR_BUFFER_BIT
SDL.SDL_GL_SwapWindow(gameWindow);
}
}
private void SDL2Panel_HandleDestroyed(object sender, EventArgs e)
{
if (!InDesignerMode)
{
glClear = null;
glClearColor = null;
glViewport = null;
SetParent(winHandle, IntPtr.Zero);
SDL.SDL_GL_DeleteContext(glContext);
glContext = IntPtr.Zero;
SDL.SDL_DestroyWindow(gameWindow);
gameWindow = IntPtr.Zero;
SDL.SDL_Quit();
}
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment