IOS7: Add iOSGraphicsManager class

The ios7 backend implements the graphic handling in the backend code.
iOS supports OpenGL through the OpenGL Framework since iOS 2.0. It's
marked as deprecated but is still shipped with the SDKs for iPhoneOS
and tvOS and will hopefully be so for some time.
The ios7 backend can therefore utilize the OpenGLGraphicsManager to
handle all graphics.

Implement an iOSGraphicsManager class that can be used in the ios7
backend. The iOSGraphicsManager will require some callback functions
in the ios7 backend. createOpenGLContext() will be called to ask the
backend to create an OpenGL context in which the graphic manager can
draw. The function returns the ID of the renderbuffer which shall be
used when creating the framebuffer object this differ iOS from other
platforms). A custom RenderBufferTarget class is added to address
this.

destroyOpenGLContext() will be called to make sure that the old GLES
context is not reused. notifyContextDestroy() does call the function
OpenGLContext.reset() but that will not destroy the context.

refreshScreen() will be called to ask the backend to present the
drawn graphics on the screen. getSystemHiDPIScreenFactor() is called
to get the screen scaling factor. getScreenWidth() and
getScreenHeight() are called to get the width and height of the
surface to draw on.

This commit adds the class but the ios7 backend doesn't make use of
it quite yet. To use it require the ios7 to be a child class of the
ModularGraphicsBackend. That change requires a lot of changes which
will be targeted in separate commits.

Update docportal and github ci worker to only disable the feature
opengl_classic_game since opengl and opengl_shaders are required to
compile the OpenGLGraphicsManager.
This commit is contained in:
Lars Sundström 2023-05-31 08:02:38 +02:00
parent adda0dc063
commit e6232547d5
11 changed files with 411 additions and 3 deletions

View File

@ -105,7 +105,7 @@ jobs:
brewPackages: a52dec faad2 flac fluid-synth freetype fribidi giflib jpeg mad libmikmod libmpeg2 libogg libpng libvorbis libvpx sdl2 sdl2_net theora
- platform: ios7
buildFlags: -scheme ScummVM-iOS CODE_SIGN_IDENTITY="" CODE_SIGNING_ALLOWED=NO
configFlags: --use-xcframework --enable-faad --enable-gif --enable-mikmod --enable-mpeg2 --enable-vpx --disable-nasm --disable-opengl --disable-taskbar --disable-tts
configFlags: --use-xcframework --enable-faad --enable-gif --enable-mikmod --enable-mpeg2 --enable-vpx --disable-nasm --disable-opengl_game_classic --disable-taskbar --disable-tts
packagesUrl: https://downloads.scummvm.org/frs/build/scummvm-ios7-libs-v3.zip
env:
BUILDCACHE_MAX_CACHE_SIZE: 2000000000

View File

@ -0,0 +1,114 @@
/* ScummVM - Graphic Adventure Engine
*
* ScummVM is the legal property of its developers, whose names
* are too numerous to list here. Please refer to the COPYRIGHT
* file distributed with this source distribution.
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
*/
#define FORBIDDEN_SYMBOL_ALLOW_ALL
#include "backends/graphics/ios/ios-graphics.h"
#include "backends/graphics/ios/renderbuffer.h"
#include "backends/graphics/opengl/pipelines/pipeline.h"
#include "backends/platform/ios7/ios7_osys_main.h"
iOSGraphicsManager::iOSGraphicsManager() {
initSurface();
}
iOSGraphicsManager::~iOSGraphicsManager() {
deinitSurface();
}
void iOSGraphicsManager::initSurface() {
OSystem_iOS7 *sys = dynamic_cast<OSystem_iOS7 *>(g_system);
// Create OpenGL context
GLuint rbo = sys->createOpenGLContext();
notifyContextCreate(OpenGL::kContextGLES2,
new OpenGL::RenderbufferTarget(rbo),
// Currently iOS runs the ARMs in little-endian mode but prepare if
// that is changed in the future.
#ifdef SCUMM_LITTLE_ENDIAN
Graphics::PixelFormat(4, 8, 8, 8, 8, 0, 8, 16, 24),
Graphics::PixelFormat(4, 8, 8, 8, 8, 0, 8, 16, 24));
#else
Graphics::PixelFormat(4, 8, 8, 8, 8, 24, 16, 8, 0),
Graphics::PixelFormat(4, 8, 8, 8, 8, 24, 16, 8, 0));
#endif
handleResize(sys->getScreenWidth(), sys->getScreenHeight());
}
void iOSGraphicsManager::deinitSurface() {
notifyContextDestroy();
dynamic_cast<OSystem_iOS7 *>(g_system)->destroyOpenGLContext();
}
void iOSGraphicsManager::notifyResize(const int width, const int height) {
handleResize(width, height);
}
iOSCommonGraphics::State iOSGraphicsManager::getState() const {
State state;
state.screenWidth = getWidth();
state.screenHeight = getHeight();
state.aspectRatio = getFeatureState(OSystem::kFeatureAspectRatioCorrection);
state.cursorPalette = getFeatureState(OSystem::kFeatureCursorPalette);
#ifdef USE_RGB_COLOR
state.pixelFormat = getScreenFormat();
#endif
return state;
}
bool iOSGraphicsManager::setState(const iOSCommonGraphics::State &state) {
beginGFXTransaction();
#ifdef USE_RGB_COLOR
initSize(state.screenWidth, state.screenHeight, &state.pixelFormat);
#else
initSize(state.screenWidth, state.screenHeight, nullptr);
#endif
setFeatureState(OSystem::kFeatureAspectRatioCorrection, state.aspectRatio);
setFeatureState(OSystem::kFeatureCursorPalette, state.cursorPalette);
return endGFXTransaction() == OSystem::kTransactionSuccess;
}
bool iOSGraphicsManager::loadVideoMode(uint requestedWidth, uint requestedHeight, const Graphics::PixelFormat &format) {
/* The iOS and tvOS video modes are always full screen */
return true;
}
float iOSGraphicsManager::getHiDPIScreenFactor() const {
return dynamic_cast<OSystem_iOS7 *>(g_system)->getSystemHiDPIScreenFactor();
}
void iOSGraphicsManager::refreshScreen() {
dynamic_cast<OSystem_iOS7 *>(g_system)->refreshScreen();
}
bool iOSGraphicsManager::notifyMousePosition(Common::Point &mouse) {
mouse.x = CLIP<int16>(mouse.x, _activeArea.drawRect.left, _activeArea.drawRect.right);
mouse.y = CLIP<int16>(mouse.y, _activeArea.drawRect.top, _activeArea.drawRect.bottom);
setMousePosition(mouse.x, mouse.y);
mouse = convertWindowToVirtual(mouse.x, mouse.y);
return true;
}

View File

@ -0,0 +1,98 @@
/* ScummVM - Graphic Adventure Engine
*
* ScummVM is the legal property of its developers, whose names
* are too numerous to list here. Please refer to the COPYRIGHT
* file distributed with this source distribution.
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
*/
#ifndef BACKENDS_GRAPHICS_IOS_IOS_GRAPHICS_H
#define BACKENDS_GRAPHICS_IOS_IOS_GRAPHICS_H
#include "common/scummsys.h"
#include <OpenGLES/ES2/gl.h>
#include "backends/graphics/opengl/opengl-graphics.h"
class iOSCommonGraphics {
public:
virtual ~iOSCommonGraphics() {}
virtual void initSurface() = 0;
virtual void deinitSurface() = 0;
/**
* Notify the graphics manager about a resize event. This happens on
* iDevices when switching to portrait mode or landscape mode.
*/
virtual void notifyResize(const int width, const int height) = 0;
virtual Common::Point getMousePosition() = 0;
virtual bool notifyMousePosition(Common::Point &mouse) = 0;
/**
* A (subset) of the graphic manager's state. This is used when switching
* between 2D and 3D graphic managers at runtime.
*/
struct State {
int screenWidth, screenHeight;
bool aspectRatio;
bool cursorPalette;
#ifdef USE_RGB_COLOR
Graphics::PixelFormat pixelFormat;
#endif
};
/**
* Gets the current state of the graphics manager.
*/
virtual State getState() const = 0;
/**
* Sets up a basic state of the graphics manager.
*/
virtual bool setState(const State &state) = 0;
};
class iOSGraphicsManager :
public OpenGL::OpenGLGraphicsManager, public iOSCommonGraphics {
public:
iOSGraphicsManager();
virtual ~iOSGraphicsManager();
void initSurface() override;
void deinitSurface() override;
void notifyResize(const int width, const int height) override;
virtual iOSCommonGraphics::State getState() const override;
virtual bool setState(const iOSCommonGraphics::State &state) override;
bool notifyMousePosition(Common::Point &mouse) override;
Common::Point getMousePosition() override { return Common::Point(_cursorX, _cursorY); }
float getHiDPIScreenFactor() const override;
protected:
void setSystemMousePosition(const int x, const int y) override {}
bool loadVideoMode(uint requestedWidth, uint requestedHeight, const Graphics::PixelFormat &format) override;
void refreshScreen() override;
};
#endif

View File

@ -0,0 +1,92 @@
/* ScummVM - Graphic Adventure Engine
*
* ScummVM is the legal property of its developers, whose names
* are too numerous to list here. Please refer to the COPYRIGHT
* file distributed with this source distribution.
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
*/
#include "backends/graphics/ios/renderbuffer.h"
#include "graphics/opengl/debug.h"
namespace OpenGL {
//
// Render to backbuffer target implementation
//
RenderbufferTarget::RenderbufferTarget(GLuint renderbufferID)
: _glRBO(renderbufferID), _glFBO(0) {
}
RenderbufferTarget::~RenderbufferTarget() {
GL_CALL_SAFE(glDeleteFramebuffers, (1, &_glFBO));
}
void RenderbufferTarget::activateInternal() {
bool needUpdate = false;
// Allocate framebuffer object if necessary.
if (!_glFBO) {
GL_CALL(glGenFramebuffers(1, &_glFBO));
needUpdate = true;
}
// Attach FBO to rendering context.
GL_CALL(glBindFramebuffer(GL_FRAMEBUFFER, _glFBO));
// Attach render buffer to newly created FBO.
if (needUpdate) {
GL_CALL(glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_RENDERBUFFER, _glRBO));
}
}
bool RenderbufferTarget::setSize(uint width, uint height) {
// Set viewport dimensions.
_viewport[0] = 0;
_viewport[1] = 0;
_viewport[2] = width;
_viewport[3] = height;
// Setup orthogonal projection matrix.
_projectionMatrix(0, 0) = 2.0f / width;
_projectionMatrix(0, 1) = 0.0f;
_projectionMatrix(0, 2) = 0.0f;
_projectionMatrix(0, 3) = 0.0f;
_projectionMatrix(1, 0) = 0.0f;
_projectionMatrix(1, 1) = -2.0f / height;
_projectionMatrix(1, 2) = 0.0f;
_projectionMatrix(1, 3) = 0.0f;
_projectionMatrix(2, 0) = 0.0f;
_projectionMatrix(2, 1) = 0.0f;
_projectionMatrix(2, 2) = 0.0f;
_projectionMatrix(2, 3) = 0.0f;
_projectionMatrix(3, 0) = -1.0f;
_projectionMatrix(3, 1) = 1.0f;
_projectionMatrix(3, 2) = 0.0f;
_projectionMatrix(3, 3) = 1.0f;
// Directly apply changes when we are active.
if (isActive()) {
applyViewport();
applyProjectionMatrix();
}
return true;
}
} // End of namespace OpenGL

View File

@ -0,0 +1,55 @@
/* ScummVM - Graphic Adventure Engine
*
* ScummVM is the legal property of its developers, whose names
* are too numerous to list here. Please refer to the COPYRIGHT
* file distributed with this source distribution.
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
*/
#ifndef BACKENDS_GRAPHICS_IOS_RENDERBUFFER_H
#define BACKENDS_GRAPHICS_IOS_RENDERBUFFER_H
#include "backends/graphics/opengl/framebuffer.h"
namespace OpenGL {
/**
* Render to renderbuffer framebuffer implementation.
*
* This target allows to render to a renderbuffer, which can then be used as
* a rendering source like expected on iOS.
*/
class RenderbufferTarget : public Framebuffer {
public:
RenderbufferTarget(GLuint renderbufferID);
~RenderbufferTarget() override;
/**
* Set size of the render target.
*/
bool setSize(uint width, uint height) override;
protected:
void activateInternal() override;
private:
GLuint _glRBO;
GLuint _glFBO;
};
} // End of namespace OpenGL
#endif

View File

@ -387,7 +387,9 @@ endif
ifdef IPHONE
MODULE_OBJS += \
mutex/pthread/pthread-mutex.o
mutex/pthread/pthread-mutex.o \
graphics/ios/ios-graphics.o \
graphics/ios/renderbuffer.o
endif
ifeq ($(BACKEND),maemo)

View File

@ -132,6 +132,13 @@ public:
bool touchpadModeEnabled() const;
uint createOpenGLContext();
void destroyOpenGLContext();
void refreshScreen() const;
int getScreenWidth() const;
int getScreenHeight() const;
float getSystemHiDPIScreenFactor() const;
#ifdef USE_RGB_COLOR
Graphics::PixelFormat getScreenFormat() const override { return _framebuffer.format; }
Common::List<Graphics::PixelFormat> getSupportedFormats() const override;

View File

@ -642,3 +642,35 @@ bool OSystem_iOS7::isKeyboardShown() const {
});
return isShown;
}
uint OSystem_iOS7::createOpenGLContext() {
// TODO: Implement creation of OpenGL context
// The context will be used by scummvm system running on
// background thread.
return 0;
}
void OSystem_iOS7::destroyOpenGLContext() {
// TODO: Implement destroy of OpenGL context
}
void OSystem_iOS7::refreshScreen() const {
// TODO: Implement presentation of the renderBuffer
// Present the renderBuffer on the openGLContext
}
int OSystem_iOS7::getScreenWidth() const {
// TODO: Return width of screen buffer
return 0;
}
int OSystem_iOS7::getScreenHeight() const {
// TODO: Return height of screen buffer
return 0;
}
float OSystem_iOS7::getSystemHiDPIScreenFactor() const {
// TODO: Return HiDPI screen factor
return 0.0;
}

4
configure vendored
View File

@ -6127,6 +6127,10 @@ if test "$_opengl_mode" != none ; then
_opengl_mode=gles2
_opengl_glad=yes
;;
ios7)
_opengl_mode=gles2
_opengl_glad=yes
;;
openpandora)
# Enable GLES only if user explicitely requested it
# Backend is SDL based so GLAD is supported

View File

@ -163,6 +163,10 @@ bool shouldSkipFileForTarget(const std::string &fileID, const std::string &targe
if (name.length() > 5 && name.substr(0, 5) == "ios7_") {
return true;
}
// macOS target: we skip all files with the "ios-" prefix
if (name.length() > 4 && name.substr(0, 4) == "ios-") {
return true;
}
// parent directory
const std::string directory = fileID.substr(0, fileID.length() - fileName.length());
static const std::string iphone_directory = "backends/platform/ios7";

View File

@ -76,7 +76,7 @@ It's time to generate the Xcode project. Run the following on the command line:
.. code::
../scummvm/devtools/create_project/xcode/build/Release/create_project ../scummvm --xcode --use-xcframework --enable-faad --enable-fluidsynth --enable-gif --enable-mikmod --enable-mpeg2 --enable-vpx --disable-nasm --disable-opengl --disable-taskbar --disable-tts
../scummvm/devtools/create_project/xcode/build/Release/create_project ../scummvm --xcode --use-xcframework --enable-faad --enable-fluidsynth --enable-gif --enable-mikmod --enable-mpeg2 --enable-vpx --disable-nasm --disable-opengl_game_classic --disable-taskbar --disable-tts
The resulting directory structure looks like this: