mirror of
https://github.com/godotengine/godot-angle-static.git
synced 2026-01-03 14:09:33 +03:00
Add a sample that uses multiple windows.
BUG=angleproject:521 Change-Id: I50858193518b4d07edcb2073caaa99ce37fcc4c3 Reviewed-on: https://chromium-review.googlesource.com/267000 Reviewed-by: Brandon Jones <bajones@chromium.org> Reviewed-by: Jamie Madill <jmadill@chromium.org> Tested-by: Geoff Lang <geofflang@chromium.org>
This commit is contained in:
186
samples/multi_window/MultiWindow.cpp
Normal file
186
samples/multi_window/MultiWindow.cpp
Normal file
@@ -0,0 +1,186 @@
|
||||
//
|
||||
// Copyright (c) 2015 The ANGLE Project Authors. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
//
|
||||
|
||||
#include "Matrix.h"
|
||||
#include "SampleApplication.h"
|
||||
#include "random_utils.h"
|
||||
#include "shader_utils.h"
|
||||
|
||||
#include <vector>
|
||||
#include <algorithm>
|
||||
|
||||
class MultiWindowSample : public SampleApplication
|
||||
{
|
||||
public:
|
||||
MultiWindowSample::MultiWindowSample()
|
||||
: SampleApplication("MultiWindow", 256, 256)
|
||||
{
|
||||
}
|
||||
|
||||
virtual bool initialize()
|
||||
{
|
||||
const std::string vs = SHADER_SOURCE
|
||||
(
|
||||
attribute vec4 vPosition;
|
||||
void main()
|
||||
{
|
||||
gl_Position = vPosition;
|
||||
}
|
||||
);
|
||||
|
||||
const std::string fs = SHADER_SOURCE
|
||||
(
|
||||
precision mediump float;
|
||||
void main()
|
||||
{
|
||||
gl_FragColor = vec4(1.0, 0.0, 0.0, 1.0);
|
||||
}
|
||||
);
|
||||
|
||||
mProgram = CompileProgram(vs, fs);
|
||||
if (!mProgram)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
// Set an initial rotation
|
||||
mRotation = 45.0f;
|
||||
|
||||
glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
|
||||
|
||||
window rootWindow;
|
||||
rootWindow.osWindow = getWindow();
|
||||
rootWindow.surface = getSurface();
|
||||
mWindows.push_back(rootWindow);
|
||||
|
||||
const size_t numWindows = 5;
|
||||
for (size_t i = 1; i < numWindows; i++)
|
||||
{
|
||||
window window;
|
||||
|
||||
window.osWindow = CreateOSWindow();
|
||||
if (!window.osWindow->initialize("MultiWindow", 256, 256))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
window.surface = eglCreateWindowSurface(getDisplay(), getConfig(), window.osWindow->getNativeWindow(), nullptr);
|
||||
if (window.surface == EGL_NO_SURFACE)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
window.osWindow->setVisible(true);
|
||||
|
||||
mWindows.push_back(window);
|
||||
}
|
||||
|
||||
for (size_t i = 1; i < mWindows.size(); i++)
|
||||
{
|
||||
int x = rootWindow.osWindow->getX() + static_cast<int>(RandomBetween(0, 512));
|
||||
int y = rootWindow.osWindow->getY() + static_cast<int>(RandomBetween(0, 512));
|
||||
int width = static_cast<int>(RandomBetween(128, 512));
|
||||
int height = static_cast<int>(RandomBetween(128, 512));
|
||||
mWindows[i].osWindow->setPosition(x, y);
|
||||
mWindows[i].osWindow->resize(width, height);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
virtual void destroy()
|
||||
{
|
||||
glDeleteProgram(mProgram);
|
||||
}
|
||||
|
||||
virtual void step(float dt, double totalTime)
|
||||
{
|
||||
mRotation = fmod(mRotation + (dt * 40.0f), 360.0f);
|
||||
}
|
||||
|
||||
virtual void draw()
|
||||
{
|
||||
OSWindow* rootWindow = mWindows[0].osWindow;
|
||||
int left = rootWindow->getX();
|
||||
int right = rootWindow->getX() + rootWindow->getWidth();
|
||||
int top = rootWindow->getY();
|
||||
int bottom = rootWindow->getY() + rootWindow->getHeight();
|
||||
for (size_t i = 1; i < mWindows.size(); i++)
|
||||
{
|
||||
OSWindow* window = mWindows[i].osWindow;
|
||||
left = std::min(left, window->getX());
|
||||
right = std::max(right, window->getX() + window->getWidth());
|
||||
top = std::min(top, window->getY());
|
||||
bottom = std::max(bottom, window->getY() + window->getHeight());
|
||||
}
|
||||
|
||||
float midX = (left + right) * 0.5f;
|
||||
float midY = (top + bottom) * 0.5f;
|
||||
|
||||
Matrix4 modelMatrix = Matrix4::translate(Vector3(midX, midY, 0.0f)) *
|
||||
Matrix4::rotate(mRotation, Vector3(0.0f, 0.0f, 1.0f)) *
|
||||
Matrix4::translate(Vector3(-midX, -midY, 0.0f));
|
||||
Matrix4 viewMatrix = Matrix4::identity();
|
||||
|
||||
for (size_t i = 0; i < mWindows.size(); i++)
|
||||
{
|
||||
OSWindow* window = mWindows[i].osWindow;
|
||||
EGLSurface surface = mWindows[i].surface;
|
||||
|
||||
eglMakeCurrent(getDisplay(), surface, surface, getContext());
|
||||
|
||||
Matrix4 orthoMatrix = Matrix4::ortho(static_cast<float>(window->getX()), static_cast<float>(window->getX() + window->getWidth()),
|
||||
static_cast<float>(window->getY() + window->getHeight()), static_cast<float>(window->getY()),
|
||||
0.0f, 1.0f);
|
||||
Matrix4 mvpMatrix = orthoMatrix * viewMatrix * modelMatrix;
|
||||
|
||||
Vector3 vertices[] =
|
||||
{
|
||||
Matrix4::transform(mvpMatrix, Vector4(midX, static_cast<float>(top), 0.0f, 1.0f)),
|
||||
Matrix4::transform(mvpMatrix, Vector4(static_cast<float>(left), static_cast<float>(bottom), 0.0f, 1.0f)),
|
||||
Matrix4::transform(mvpMatrix, Vector4(static_cast<float>(right), static_cast<float>(bottom), 0.0f, 1.0f)),
|
||||
};
|
||||
|
||||
// Set the viewport
|
||||
glViewport(0, 0, window->getWidth(), window->getHeight());
|
||||
|
||||
// Clear the color buffer
|
||||
glClear(GL_COLOR_BUFFER_BIT);
|
||||
|
||||
// Use the program object
|
||||
glUseProgram(mProgram);
|
||||
|
||||
// Load the vertex data
|
||||
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 0, vertices[0].data);
|
||||
glEnableVertexAttribArray(0);
|
||||
|
||||
glDrawArrays(GL_TRIANGLES, 0, 3);
|
||||
|
||||
eglSwapBuffers(getDisplay(), surface);
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
// Handle to a program object
|
||||
GLuint mProgram;
|
||||
|
||||
// Current rotation
|
||||
float mRotation;
|
||||
|
||||
// Window and surface data
|
||||
struct window
|
||||
{
|
||||
OSWindow* osWindow;
|
||||
EGLSurface surface;
|
||||
};
|
||||
std::vector<window> mWindows;
|
||||
};
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
MultiWindowSample app;
|
||||
return app.run();
|
||||
}
|
||||
@@ -100,6 +100,14 @@
|
||||
]
|
||||
},
|
||||
|
||||
{
|
||||
'target_name': 'multi_window',
|
||||
'type': 'executable',
|
||||
'dependencies': [ 'sample_util' ],
|
||||
'includes': [ '../build/common_defines.gypi', ],
|
||||
'sources': [ 'multi_window/MultiWindow.cpp', ],
|
||||
},
|
||||
|
||||
{
|
||||
'target_name': 'multiple_draw_buffers',
|
||||
'type': 'executable',
|
||||
|
||||
@@ -7,7 +7,9 @@
|
||||
#include "OSWindow.h"
|
||||
|
||||
OSWindow::OSWindow()
|
||||
: mWidth(0),
|
||||
: mX(0),
|
||||
mY(0),
|
||||
mWidth(0),
|
||||
mHeight(0)
|
||||
{
|
||||
}
|
||||
@@ -15,6 +17,16 @@ OSWindow::OSWindow()
|
||||
OSWindow::~OSWindow()
|
||||
{}
|
||||
|
||||
int OSWindow::getX() const
|
||||
{
|
||||
return mX;
|
||||
}
|
||||
|
||||
int OSWindow::getY() const
|
||||
{
|
||||
return mY;
|
||||
}
|
||||
|
||||
int OSWindow::getWidth() const
|
||||
{
|
||||
return mWidth;
|
||||
@@ -43,6 +55,10 @@ void OSWindow::pushEvent(Event event)
|
||||
{
|
||||
switch (event.Type)
|
||||
{
|
||||
case Event::EVENT_MOVED:
|
||||
mX = event.Move.X;
|
||||
mY = event.Move.Y;
|
||||
break;
|
||||
case Event::EVENT_RESIZED:
|
||||
mWidth = event.Size.Width;
|
||||
mHeight = event.Size.Height;
|
||||
|
||||
@@ -22,6 +22,8 @@ class OSWindow
|
||||
virtual bool initialize(const std::string &name, size_t width, size_t height) = 0;
|
||||
virtual void destroy() = 0;
|
||||
|
||||
int getX() const;
|
||||
int getY() const;
|
||||
int getWidth() const;
|
||||
int getHeight() const;
|
||||
|
||||
@@ -34,6 +36,7 @@ class OSWindow
|
||||
virtual void pushEvent(Event event);
|
||||
|
||||
virtual void setMousePosition(int x, int y) = 0;
|
||||
virtual bool setPosition(int x, int y) = 0;
|
||||
virtual bool resize(int width, int height) = 0;
|
||||
virtual void setVisible(bool isVisible) = 0;
|
||||
|
||||
@@ -43,6 +46,8 @@ class OSWindow
|
||||
bool didTestEventFire();
|
||||
|
||||
protected:
|
||||
int mX;
|
||||
int mY;
|
||||
int mWidth;
|
||||
int mHeight;
|
||||
|
||||
|
||||
@@ -518,6 +518,27 @@ OSWindow *CreateOSWindow()
|
||||
return new Win32Window();
|
||||
}
|
||||
|
||||
bool Win32Window::setPosition(int x, int y)
|
||||
{
|
||||
if (mX == x && mY == mY)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
RECT windowRect;
|
||||
if (!GetWindowRect(mParentWindow, &windowRect))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!MoveWindow(mParentWindow, x, y, windowRect.right - windowRect.left, windowRect.bottom - windowRect.top, TRUE))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Win32Window::resize(int width, int height)
|
||||
{
|
||||
if (width == mWidth && height == mHeight)
|
||||
@@ -539,7 +560,7 @@ bool Win32Window::resize(int width, int height)
|
||||
|
||||
LONG diffX = (windowRect.right - windowRect.left) - clientRect.right;
|
||||
LONG diffY = (windowRect.bottom - windowRect.top) - clientRect.bottom;
|
||||
if (!MoveWindow(mParentWindow, windowRect.left, windowRect.top, width + diffX, height + diffY, FALSE))
|
||||
if (!MoveWindow(mParentWindow, windowRect.left, windowRect.top, width + diffX, height + diffY, TRUE))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -28,6 +28,7 @@ class Win32Window : public OSWindow
|
||||
void pushEvent(Event event) override;
|
||||
|
||||
void setMousePosition(int x, int y) override;
|
||||
bool setPosition(int x, int y) override;
|
||||
bool resize(int width, int height) override;
|
||||
void setVisible(bool isVisible) override;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user