mirror of https://github.com/buggins/dlangui.git
fix #168 - share OpenGL context between windows under Win32/OpenGL
This commit is contained in:
parent
3c5573aba0
commit
f9780e268e
|
@ -102,7 +102,10 @@ extern (C) int UIAppMain(string[] args) {
|
||||||
cam.translation = vec3(0, 0, -5);
|
cam.translation = vec3(0, 0, -5);
|
||||||
scene.activeCamera = cam;
|
scene.activeCamera = cam;
|
||||||
mat4 camMatrix = scene.viewProjectionMatrix;
|
mat4 camMatrix = scene.viewProjectionMatrix;
|
||||||
MeshPart part = new MeshPart();
|
VertexFormat vfmt = VertexFormat(VertexElementType.POSITION, VertexElementType.COLOR, VertexElementType.TEXCOORD0);
|
||||||
|
Mesh2 mesh = new Mesh2(vfmt);
|
||||||
|
mesh.addVertex([1,2,3, 1,1,1,1, 0,0]);
|
||||||
|
//MeshPart part = new MeshPart();
|
||||||
|
|
||||||
// show window
|
// show window
|
||||||
window.show();
|
window.show();
|
||||||
|
|
|
@ -86,7 +86,11 @@ struct FileFilterEntry {
|
||||||
}
|
}
|
||||||
|
|
||||||
version (Windows) {
|
version (Windows) {
|
||||||
__gshared bool SHOW_FILE_DIALOG_IN_POPUP = true;
|
static if (BACKEND_SDL) {
|
||||||
|
__gshared bool SHOW_FILE_DIALOG_IN_POPUP = false;
|
||||||
|
} else {
|
||||||
|
__gshared bool SHOW_FILE_DIALOG_IN_POPUP = false;
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
__gshared bool SHOW_FILE_DIALOG_IN_POPUP = false;
|
__gshared bool SHOW_FILE_DIALOG_IN_POPUP = false;
|
||||||
}
|
}
|
||||||
|
|
|
@ -22,7 +22,21 @@ struct VertexElement {
|
||||||
private ubyte _size;
|
private ubyte _size;
|
||||||
@property VertexElementType type() const { return _type; }
|
@property VertexElementType type() const { return _type; }
|
||||||
@property ubyte size() const { return _size; }
|
@property ubyte size() const { return _size; }
|
||||||
this(VertexElementType type, ubyte size) {
|
this(VertexElementType type, ubyte size = 0) {
|
||||||
|
if (size == 0) {
|
||||||
|
switch(type) with (VertexElementType) {
|
||||||
|
case POSITION:
|
||||||
|
case NORMAL:
|
||||||
|
size = 3;
|
||||||
|
break;
|
||||||
|
case COLOR:
|
||||||
|
size = 4;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
size = 2;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
_type = type;
|
_type = type;
|
||||||
_size = size;
|
_size = size;
|
||||||
}
|
}
|
||||||
|
@ -38,6 +52,14 @@ struct VertexFormat {
|
||||||
foreach(elem; elems)
|
foreach(elem; elems)
|
||||||
_vertexSize += elem.size * float.sizeof;
|
_vertexSize += elem.size * float.sizeof;
|
||||||
}
|
}
|
||||||
|
/// init from vertex element types, using default sizes for types
|
||||||
|
this(inout VertexElementType[] types...) {
|
||||||
|
foreach(t; types) {
|
||||||
|
VertexElement elem = VertexElement(t);
|
||||||
|
_elements ~= elem;
|
||||||
|
_vertexSize += elem.size;
|
||||||
|
}
|
||||||
|
}
|
||||||
/// get number of elements
|
/// get number of elements
|
||||||
@property int length() const {
|
@property int length() const {
|
||||||
return cast(int)_elements.length;
|
return cast(int)_elements.length;
|
||||||
|
@ -46,10 +68,24 @@ struct VertexFormat {
|
||||||
VertexElement opIndex(int index) const {
|
VertexElement opIndex(int index) const {
|
||||||
return _elements[index];
|
return _elements[index];
|
||||||
}
|
}
|
||||||
/// returns vertex size in bytes for format
|
/// returns vertex size in bytes
|
||||||
@property int vertexSize() const {
|
@property int vertexSize() const {
|
||||||
|
return _vertexSize * float.sizeof;
|
||||||
|
}
|
||||||
|
/// returns vertex size in floats
|
||||||
|
@property int vertexFloats() const {
|
||||||
return _vertexSize;
|
return _vertexSize;
|
||||||
}
|
}
|
||||||
|
/// returns true if it's valid vertex format
|
||||||
|
@property bool isValid() const {
|
||||||
|
if (!_vertexSize)
|
||||||
|
return false;
|
||||||
|
foreach(elem; _elements) {
|
||||||
|
if (elem.type == VertexElementType.POSITION)
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
/// compare
|
/// compare
|
||||||
bool opEquals(immutable ref VertexFormat fmt) {
|
bool opEquals(immutable ref VertexFormat fmt) {
|
||||||
if (_vertexSize != fmt._vertexSize)
|
if (_vertexSize != fmt._vertexSize)
|
||||||
|
@ -61,6 +97,46 @@ struct VertexFormat {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
class Mesh2 {
|
||||||
|
protected VertexFormat _vertexFormat;
|
||||||
|
protected int _vertexCount;
|
||||||
|
protected float[] _vertexData;
|
||||||
|
|
||||||
|
@property ref const(VertexFormat) vertexFormat() const { return _vertexFormat; }
|
||||||
|
@property void vertexFormat(VertexFormat format) {
|
||||||
|
assert(_vertexCount == 0);
|
||||||
|
_vertexFormat = format;
|
||||||
|
}
|
||||||
|
@property int vertexCount() const { return _vertexCount; }
|
||||||
|
|
||||||
|
/// adds single vertex
|
||||||
|
int addVertex(float[] data) {
|
||||||
|
assert(_vertexFormat.isValid && data.length == _vertexFormat.vertexFloats);
|
||||||
|
int res = _vertexCount;
|
||||||
|
_vertexData.assumeSafeAppend();
|
||||||
|
_vertexData ~= data;
|
||||||
|
_vertexCount++;
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// adds one or more vertexes
|
||||||
|
int addVertexes(float[] data) {
|
||||||
|
assert(_vertexFormat.isValid && (data.length > 0) && (data.length % _vertexFormat.vertexFloats == 0));
|
||||||
|
int res = _vertexCount;
|
||||||
|
_vertexData.assumeSafeAppend();
|
||||||
|
_vertexData ~= data;
|
||||||
|
_vertexCount += cast(int)(data.length / _vertexFormat.vertexFloats);
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
|
||||||
|
this() {
|
||||||
|
}
|
||||||
|
|
||||||
|
this(VertexFormat vertexFormat) {
|
||||||
|
_vertexFormat = vertexFormat;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
class Mesh {
|
class Mesh {
|
||||||
protected MeshPart[] _parts;
|
protected MeshPart[] _parts;
|
||||||
protected int _vertexCount;
|
protected int _vertexCount;
|
||||||
|
|
|
@ -156,6 +156,69 @@ static if (ENABLE_OPENGL) {
|
||||||
|
|
||||||
const uint CUSTOM_MESSAGE_ID = WM_USER + 1;
|
const uint CUSTOM_MESSAGE_ID = WM_USER + 1;
|
||||||
|
|
||||||
|
static if (ENABLE_OPENGL) {
|
||||||
|
|
||||||
|
/// Shared opengl context helper
|
||||||
|
struct SharedGLContext {
|
||||||
|
import derelict.opengl3.wgl;
|
||||||
|
|
||||||
|
HGLRC _hGLRC; // opengl context
|
||||||
|
HPALETTE _hPalette;
|
||||||
|
bool _error;
|
||||||
|
/// Init OpenGL context, if not yet initialized
|
||||||
|
bool init(HDC hDC) {
|
||||||
|
if (_hGLRC)
|
||||||
|
return true;
|
||||||
|
if (_error)
|
||||||
|
return false;
|
||||||
|
if (setupPixelFormat(hDC)) {
|
||||||
|
_hPalette = setupPalette(hDC);
|
||||||
|
_hGLRC = wglCreateContext(hDC);
|
||||||
|
if (_hGLRC) {
|
||||||
|
bind(hDC);
|
||||||
|
bool initialized = initGLSupport(false);
|
||||||
|
unbind(hDC);
|
||||||
|
if (!initialized) {
|
||||||
|
uninit();
|
||||||
|
Log.e("Failed to init OpenGL shaders");
|
||||||
|
_error = true;
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
} else {
|
||||||
|
_error = true;
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
Log.e("Cannot setup pixel format");
|
||||||
|
_error = true;
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
void uninit() {
|
||||||
|
if (_hGLRC) {
|
||||||
|
wglDeleteContext(_hGLRC);
|
||||||
|
_hGLRC = null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/// make this context current for DC
|
||||||
|
void bind(HDC hDC) {
|
||||||
|
wglMakeCurrent(hDC, _hGLRC);
|
||||||
|
}
|
||||||
|
/// make null context current for DC
|
||||||
|
void unbind(HDC hDC) {
|
||||||
|
wglMakeCurrent(hDC, null);
|
||||||
|
}
|
||||||
|
void swapBuffers(HDC hDC) {
|
||||||
|
SwapBuffers(hDC);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/// OpenGL context to share between windows
|
||||||
|
__gshared SharedGLContext sharedGLContext;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
class Win32Window : Window {
|
class Win32Window : Window {
|
||||||
Win32Platform _platform;
|
Win32Platform _platform;
|
||||||
|
|
||||||
|
@ -200,25 +263,11 @@ class Win32Window : Window {
|
||||||
_hInstance, // program instance handle
|
_hInstance, // program instance handle
|
||||||
cast(void*)this); // creation parameters
|
cast(void*)this); // creation parameters
|
||||||
static if (ENABLE_OPENGL) {
|
static if (ENABLE_OPENGL) {
|
||||||
import derelict.opengl3.wgl;
|
|
||||||
|
|
||||||
/* initialize OpenGL rendering */
|
/* initialize OpenGL rendering */
|
||||||
HDC hDC = GetDC(_hwnd);
|
HDC hDC = GetDC(_hwnd);
|
||||||
|
|
||||||
if (openglEnabled || !_glSupport) {
|
if (openglEnabled || !_glSupport) {
|
||||||
if (setupPixelFormat(hDC)) {
|
useOpengl = sharedGLContext.init(hDC);
|
||||||
_hPalette = setupPalette(hDC);
|
|
||||||
_hGLRC = wglCreateContext(hDC);
|
|
||||||
if (_hGLRC) {
|
|
||||||
wglMakeCurrent(hDC, _hGLRC);
|
|
||||||
useOpengl = initGLSupport(false);
|
|
||||||
wglMakeCurrent(hDC, null);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
Log.e("Pixelformat failed");
|
|
||||||
// disable GL
|
|
||||||
useOpengl = false;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -239,7 +288,7 @@ class Win32Window : Window {
|
||||||
//HDC hdc = BeginPaint(_hwnd, &ps);
|
//HDC hdc = BeginPaint(_hwnd, &ps);
|
||||||
//scope(exit) EndPaint(_hwnd, &ps);
|
//scope(exit) EndPaint(_hwnd, &ps);
|
||||||
HDC hdc = GetDC(_hwnd);
|
HDC hdc = GetDC(_hwnd);
|
||||||
wglMakeCurrent(hdc, _hGLRC);
|
sharedGLContext.bind(hdc);
|
||||||
//_glSupport = _gl;
|
//_glSupport = _gl;
|
||||||
glDisable(GL_DEPTH_TEST);
|
glDisable(GL_DEPTH_TEST);
|
||||||
glViewport(0, 0, _dx, _dy);
|
glViewport(0, 0, _dx, _dy);
|
||||||
|
@ -267,14 +316,15 @@ class Win32Window : Window {
|
||||||
onDraw(buf);
|
onDraw(buf);
|
||||||
}
|
}
|
||||||
buf.afterDrawing();
|
buf.afterDrawing();
|
||||||
SwapBuffers(hdc);
|
sharedGLContext.swapBuffers(hdc);
|
||||||
wglMakeCurrent(hdc, null);
|
sharedGLContext.unbind(hdc);
|
||||||
destroy(buf);
|
destroy(buf);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
~this() {
|
~this() {
|
||||||
debug Log.d("Window destructor");
|
debug Log.d("Window destructor");
|
||||||
|
/*
|
||||||
static if (ENABLE_OPENGL) {
|
static if (ENABLE_OPENGL) {
|
||||||
import derelict.opengl3.wgl;
|
import derelict.opengl3.wgl;
|
||||||
if (_hGLRC) {
|
if (_hGLRC) {
|
||||||
|
@ -287,6 +337,7 @@ class Win32Window : Window {
|
||||||
_hGLRC = null;
|
_hGLRC = null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
*/
|
||||||
if (_hwnd)
|
if (_hwnd)
|
||||||
DestroyWindow(_hwnd);
|
DestroyWindow(_hwnd);
|
||||||
_hwnd = null;
|
_hwnd = null;
|
||||||
|
|
Loading…
Reference in New Issue