summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/CMakeLists.txt64
-rw-r--r--src/client.cpp131
-rw-r--r--src/client.h13
-rw-r--r--src/compoundsprite.cpp18
-rw-r--r--src/cpp0x_compat/cstdint10
-rw-r--r--src/event.cpp24
-rw-r--r--src/event.h24
-rw-r--r--src/game.cpp6
-rw-r--r--src/graphics.cpp451
-rw-r--r--src/graphics.h108
-rw-r--r--src/gui/gui.cpp18
-rw-r--r--src/gui/gui.h2
-rw-r--r--src/gui/sdlinput.cpp120
-rw-r--r--src/gui/sdlinput.h22
-rw-r--r--src/gui/setup.cpp6
-rw-r--r--src/gui/setup_keyboard.cpp4
-rw-r--r--src/gui/setup_video.cpp37
-rw-r--r--src/gui/socialwindow.cpp5
-rw-r--r--src/gui/tradewindow.h2
-rw-r--r--src/gui/truetypefont.cpp4
-rw-r--r--src/gui/viewport.cpp2
-rw-r--r--src/gui/widgets/button.cpp2
-rw-r--r--src/gui/widgets/desktop.cpp24
-rw-r--r--src/gui/widgets/dropdown.cpp2
-rw-r--r--src/gui/widgets/emoteshortcutcontainer.cpp2
-rw-r--r--src/gui/widgets/itemshortcutcontainer.cpp2
-rw-r--r--src/gui/widgets/playerbox.cpp2
-rw-r--r--src/gui/widgets/progressbar.cpp2
-rw-r--r--src/gui/widgets/scrollarea.cpp6
-rw-r--r--src/gui/widgets/tab.cpp2
-rw-r--r--src/gui/widgets/textfield.cpp46
-rw-r--r--src/gui/widgets/textfield.h6
-rw-r--r--src/gui/windowmenu.cpp2
-rw-r--r--src/guild.cpp2
-rw-r--r--src/joystick.cpp2
-rw-r--r--src/keyboardconfig.cpp6
-rw-r--r--src/keyboardconfig.h2
-rw-r--r--src/net/download.cpp2
-rw-r--r--src/net/manaserv/messagehandler.h2
-rw-r--r--src/net/manaserv/messagein.h5
-rw-r--r--src/net/tmwa/loginhandler.cpp2
-rw-r--r--src/net/tmwa/messagehandler.h2
-rw-r--r--src/net/tmwa/messagein.h5
-rw-r--r--src/net/tmwa/network.cpp4
-rw-r--r--src/net/tmwa/tradehandler.cpp5
-rw-r--r--src/openglgraphics.cpp85
-rw-r--r--src/openglgraphics.h9
-rw-r--r--src/party.cpp2
-rw-r--r--src/resources/ambientlayer.cpp22
-rw-r--r--src/resources/image.cpp291
-rw-r--r--src/resources/image.h58
-rw-r--r--src/resources/settingsmanager.cpp4
-rw-r--r--src/resources/theme.cpp4
-rw-r--r--src/sound.cpp4
-rw-r--r--src/utils/copynpaste.cpp310
-rw-r--r--src/utils/copynpaste.h10
-rw-r--r--src/utils/dtor.h6
-rw-r--r--src/utils/mutex.h4
-rw-r--r--src/utils/physfsrwops.h9
-rw-r--r--src/utils/stringutils.cpp2
-rw-r--r--src/vector.h8
61 files changed, 778 insertions, 1258 deletions
diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt
index b40eab7b..695fef36 100644
--- a/src/CMakeLists.txt
+++ b/src/CMakeLists.txt
@@ -1,9 +1,10 @@
-FIND_PACKAGE(SDL REQUIRED)
-FIND_PACKAGE(SDL_image REQUIRED)
-FIND_PACKAGE(SDL_mixer REQUIRED)
-FIND_PACKAGE(SDL_net REQUIRED)
-FIND_PACKAGE(SDL_ttf REQUIRED)
-FIND_PACKAGE(SDL_gfx REQUIRED)
+include(FindPkgConfig)
+pkg_check_modules(SDL2 REQUIRED sdl2>=2.0.1)
+pkg_check_modules(SDL2IMAGE REQUIRED SDL2_image)
+pkg_check_modules(SDL2MIXER REQUIRED SDL2_mixer)
+pkg_check_modules(SDL2NET REQUIRED SDL2_net)
+pkg_check_modules(SDL2TTF REQUIRED SDL2_ttf)
+pkg_check_modules(SDL2GFX REQUIRED SDL2_gfx)
FIND_PACKAGE(CURL REQUIRED)
FIND_PACKAGE(LibXml2 REQUIRED)
FIND_PACKAGE(PhysFS REQUIRED)
@@ -34,11 +35,6 @@ ENDIF()
SET(FLAGS "-DPACKAGE_VERSION=\\\"${VERSION}\\\"")
SET(FLAGS "${FLAGS} -DPKG_DATADIR=\\\"${PKG_DATADIR}/\\\"")
SET(FLAGS "${FLAGS} -DLOCALEDIR=\\\"${LOCALEDIR}/\\\"")
-IF (ENABLE_CPP0X)
- SET(FLAGS "${FLAGS} -std=c++0x -DENABLE_CPP0X=1")
-ELSE()
- INCLUDE_DIRECTORIES("cpp0x_compat")
-ENDIF()
IF (ENABLE_NLS)
SET(FLAGS "${FLAGS} -DENABLE_NLS=1")
@@ -69,8 +65,7 @@ ELSEIF (CMAKE_SYSTEM_NAME STREQUAL SunOS)
SET(EXTRA_LIBRARIES intl)
ENDIF()
-SET(GUICHAN_COMPONENTS "SDL")
-FIND_PACKAGE(Guichan REQUIRED ${GUICHAN_COMPONENTS})
+FIND_PACKAGE(Guichan REQUIRED)
IF (WITH_OPENGL)
FIND_PACKAGE(OpenGL REQUIRED)
@@ -79,20 +74,14 @@ IF (WITH_OPENGL)
MESSAGE(STATUS "OpenGL support enabled")
ENDIF (WITH_OPENGL)
-IF (USE_X11)
- FIND_PACKAGE(X11 REQUIRED)
- INCLUDE_DIRECTORIES(${X11_INCLUDE_DIR})
- SET(FLAGS "${FLAGS} -DUSE_X11")
-ENDIF (USE_X11)
-
INCLUDE_DIRECTORIES(
${CMAKE_CURRENT_SOURCE_DIR}
- ${SDL_INCLUDE_DIR}
- ${SDLIMAGE_INCLUDE_DIR}
- ${SDLMIXER_INCLUDE_DIR}
- ${SDLNET_INCLUDE_DIR}
- ${SDLTTF_INCLUDE_DIR}
- ${SDLGFX_INCLUDE_DIR}
+ ${SDL2_INCLUDE_DIRS}
+ ${SDL2IMAGE_INCLUDE_DIRS}
+ ${SDL2MIXER_INCLUDE_DIRS}
+ ${SDL2NET_INCLUDE_DIRS}
+ ${SDL2TTF_INCLUDE_DIRS}
+ ${SDL2GFX_INCLUDE_DIRS}
${PNG_INCLUDE_DIR}
${PHYSFS_INCLUDE_DIR}
${CURL_INCLUDE_DIR}
@@ -116,19 +105,6 @@ IF (MINGW)
"<CMAKE_RC_COMPILER> <FLAGS> <DEFINES> -O coff -o <OBJECT> <SOURCE>")
ENDIF()
-# Fix some stuff that gets not hidden by mainline modules
-MARK_AS_ADVANCED(PHYSFS_INCLUDE_DIR)
-MARK_AS_ADVANCED(PHYSFS_LIBRARY)
-MARK_AS_ADVANCED(SDLIMAGE_INCLUDE_DIR)
-MARK_AS_ADVANCED(SDLIMAGE_LIBRARY)
-MARK_AS_ADVANCED(SDLMAIN_LIBRARY)
-MARK_AS_ADVANCED(SDLMIXER_INCLUDE_DIR)
-MARK_AS_ADVANCED(SDLMIXER_LIBRARY)
-MARK_AS_ADVANCED(SDLNET_INCLUDE_DIR)
-MARK_AS_ADVANCED(SDLNET_LIBRARY)
-MARK_AS_ADVANCED(SDL_INCLUDE_DIR)
-MARK_AS_ADVANCED(SDL_LIBRARY)
-
SET(SRCS
gui/widgets/avatarlistbox.cpp
gui/widgets/avatarlistbox.h
@@ -679,12 +655,12 @@ ENDIF(ENABLE_MANASERV)
TARGET_LINK_LIBRARIES(mana
${INTERNAL_LIBRARIES}
- ${SDLGFX_LIBRARIES}
- ${SDL_LIBRARY}
- ${SDLIMAGE_LIBRARY}
- ${SDLMIXER_LIBRARY}
- ${SDLNET_LIBRARY}
- ${SDLTTF_LIBRARY}
+ ${SDL2_LIBRARIES}
+ ${SDL2GFX_LIBRARIES}
+ ${SDL2IMAGE_LIBRARIES}
+ ${SDL2MIXER_LIBRARIES}
+ ${SDL2NET_LIBRARIES}
+ ${SDL2TTF_LIBRARIES}
${PNG_LIBRARIES}
${PHYSFS_LIBRARY}
${CURL_LIBRARIES}
diff --git a/src/client.cpp b/src/client.cpp
index 1489a0dc..0db7efa6 100644
--- a/src/client.cpp
+++ b/src/client.cpp
@@ -34,7 +34,6 @@
#endif
#include "playerrelations.h"
#include "sound.h"
-#include "statuseffect.h"
#include "units.h"
#include "gui/changeemaildialog.h"
@@ -66,12 +65,8 @@
#include "resources/chardb.h"
#include "resources/hairdb.h"
-#include "resources/emotedb.h"
#include "resources/image.h"
#include "resources/itemdb.h"
-#include "resources/monsterdb.h"
-#include "resources/specialdb.h"
-#include "resources/npcdb.h"
#include "resources/resourcemanager.h"
#include "resources/theme.h"
#include "resources/userpalette.h"
@@ -241,11 +236,6 @@ Client::Client(const Options &options):
}
atexit(SDL_Quit);
- SDL_EnableUNICODE(1);
- SDL_EnableKeyRepeat(SDL_DEFAULT_REPEAT_DELAY, SDL_DEFAULT_REPEAT_INTERVAL);
-
- SDL_WM_SetCaption(branding.getValue("appName", "Mana").c_str(), NULL);
-
ResourceManager *resman = ResourceManager::getInstance();
if (!resman->setWriteDir(mLocalDataDir))
@@ -254,8 +244,6 @@ Client::Client(const Options &options):
"Exiting.", mLocalDataDir.c_str()));
}
- Image::SDLsetEnableAlphaCache(config.getValue("alphaCache", true));
-
#if defined __APPLE__
CFBundleRef mainBundle = CFBundleGetMainBundle();
CFURLRef resourcesURL = CFBundleCopyResourcesDirectoryURL(mainBundle);
@@ -300,6 +288,39 @@ Client::Client(const Options &options):
// Add the local data directory to PhysicsFS search path
resman->addToSearchPath(mLocalDataDir, false);
+ bool useOpenGL = !mOptions.noOpenGL && (config.getValue("opengl", 1) == 1);
+
+ // Set up the transparency option for low CPU when not using OpenGL.
+ if (!useOpenGL && (config.getValue("disableTransparency", 0) == 1))
+ Image::SDLdisableTransparency();
+
+#ifdef USE_OPENGL
+ // Setup image loading for the right image format
+ Image::setLoadAsOpenGL(useOpenGL);
+
+ // Create the graphics context
+ graphics = useOpenGL ? new OpenGLGraphics : new Graphics;
+#else
+ // Create the graphics context
+ graphics = new Graphics;
+#endif
+
+ const int width = config.getIntValue("screenwidth");
+ const int height = config.getIntValue("screenheight");
+ const bool fullscreen = config.getBoolValue("screen");
+
+ // Try to set the desired video mode
+ if (!graphics->setVideoMode(width, height, fullscreen))
+ {
+ logger->error(strprintf("Couldn't set %dx%d video mode: %s",
+ width, height, SDL_GetError()));
+ }
+
+ SDL_SetWindowTitle(graphics->getTarget(),
+ branding.getValue("appName", "Mana").c_str());
+
+ Image::setRenderer(graphics->getRenderer());
+
std::string iconFile = branding.getValue("appIcon", "icons/mana");
#ifdef _WIN32
iconFile += ".ico";
@@ -325,42 +346,10 @@ Client::Client(const Options &options):
mIcon = IMG_Load(iconFile.c_str());
if (mIcon)
{
- SDL_SetAlpha(mIcon, SDL_SRCALPHA, SDL_ALPHA_OPAQUE);
- SDL_WM_SetIcon(mIcon, NULL);
+ SDL_SetWindowIcon(graphics->getTarget(), mIcon);
}
#endif
- bool useOpenGL = !mOptions.noOpenGL && (config.getValue("opengl", 1) == 1);
-
- // Set up the transparency option for low CPU when not using OpenGL.
- if (!useOpenGL && (config.getValue("disableTransparency", 0) == 1))
- Image::SDLdisableTransparency();
-
-#ifdef USE_OPENGL
-
- // Setup image loading for the right image format
- Image::setLoadAsOpenGL(useOpenGL);
-
- // Create the graphics context
- graphics = useOpenGL ? new OpenGLGraphics : new Graphics;
-#else
- // Create the graphics context
- graphics = new Graphics;
-#endif
-
- const int width = config.getIntValue("screenwidth");
- const int height = config.getIntValue("screenheight");
- const int bpp = 0;
- const bool fullscreen = config.getBoolValue("screen");
- const bool hwaccel = config.getBoolValue("hwaccel");
-
- // Try to set the desired video mode
- if (!graphics->setVideoMode(width, height, bpp, fullscreen, hwaccel))
- {
- logger->error(strprintf("Couldn't set %dx%dx%d video mode: %s",
- width, height, bpp, SDL_GetError()));
- }
-
// Initialize for drawing
graphics->_beginDraw();
@@ -511,8 +500,12 @@ int Client::exec()
case SDL_KEYDOWN:
break;
- case SDL_VIDEORESIZE:
- handleVideoResize(event.resize.w, event.resize.h);
+ case SDL_WINDOWEVENT:
+ switch (event.window.event) {
+ case SDL_WINDOWEVENT_RESIZED:
+ handleVideoResize(event.window.data1, event.window.data2);
+ break;
+ }
break;
}
@@ -761,8 +754,7 @@ int Client::exec()
// Load XML databases
CharDB::load();
- if (itemDb)
- delete itemDb;
+ delete itemDb;
switch (Net::getNetworkType())
{
@@ -1375,25 +1367,15 @@ void Client::accountLogin(LoginData *loginData)
void Client::handleVideoResize(int width, int height)
{
- // Keep a minimum size. This isn't adhered to by the actual window, but
- // it keeps some window positions from getting messed up.
- width = std::max(640, width);
- height = std::max(360, height);
-
- if (graphics->changeVideoMode(width,
- height,
- graphics->getBpp(),
- false,
- graphics->getHWAccel()))
- {
- videoResized(graphics->getWidth(),
- graphics->getHeight());
+ graphics->videoResized(width, height);
- // Since everything appears to have worked out, remember to store the
- // new size in the configuration.
- config.setValue("screenwidth", width);
- config.setValue("screenheight", height);
- }
+ // The graphics width/height may be different due to scale
+ videoResized(graphics->getWidth(), graphics->getHeight());
+
+ // Since everything appears to have worked out, remember to store the
+ // new size in the configuration.
+ config.setValue("screenwidth", width);
+ config.setValue("screenheight", height);
}
void Client::videoResized(int width, int height)
@@ -1409,3 +1391,18 @@ void Client::videoResized(int width, int height)
if (mGame)
mGame->videoResized(width, height);
}
+
+bool Client::isActive()
+{
+ return !(SDL_GetWindowFlags(graphics->getTarget()) & SDL_WINDOW_MINIMIZED);
+}
+
+bool Client::hasInputFocus()
+{
+ return SDL_GetWindowFlags(graphics->getTarget()) & SDL_WINDOW_INPUT_FOCUS;
+}
+
+bool Client::hasMouseFocus()
+{
+ return SDL_GetWindowFlags(graphics->getTarget()) & SDL_WINDOW_MOUSE_FOCUS;
+}
diff --git a/src/client.h b/src/client.h
index 4ad5562d..28fd4445 100644
--- a/src/client.h
+++ b/src/client.h
@@ -29,7 +29,7 @@
#include <guichan/actionlistener.hpp>
#include <SDL.h>
-#include <SDL_framerate.h>
+#include <SDL2_framerate.h>
#include <string>
@@ -214,14 +214,9 @@ public:
*/
void videoResized(int width, int height);
- static bool isActive()
- { return SDL_GetAppState() & SDL_APPACTIVE; }
-
- static bool hasInputFocus()
- { return SDL_GetAppState() & SDL_APPINPUTFOCUS; }
-
- static bool hasMouseFocus()
- { return SDL_GetAppState() & SDL_APPMOUSEFOCUS; }
+ static bool isActive();
+ static bool hasInputFocus();
+ static bool hasMouseFocus();
private:
void initRootDir();
diff --git a/src/compoundsprite.cpp b/src/compoundsprite.cpp
index cd07ca51..0f231535 100644
--- a/src/compoundsprite.cpp
+++ b/src/compoundsprite.cpp
@@ -20,7 +20,6 @@
#include "compoundsprite.h"
-#include "game.h"
#include "graphics.h"
#include "map.h"
@@ -223,6 +222,7 @@ int CompoundSprite::getDuration() const
return duration;
}
+#if 0
static void updateValues(int &dimension, int &pos, int imgDimUL, int imgDimRD, int imgOffset)
{
// Handle going beyond the left/up
@@ -238,11 +238,18 @@ static void updateValues(int &dimension, int &pos, int imgDimUL, int imgDimRD, i
if (temp > dimension)
dimension = temp;
}
-
-#include "localplayer.h"
+#endif
void CompoundSprite::redraw() const
{
+#if 1 // TODO_SDL2: Does it make sense to implement CompoundSprite?
+ mWidth = mSprites.at(0)->getWidth();
+ mHeight = mSprites.at(0)->getHeight();
+ mOffsetX = 0;
+ mOffsetY = 0;
+ mNeedsRedraw = false;
+#else
+
#ifdef USE_OPENGL
// TODO OpenGL support
if (Image::getLoadAsOpenGL())
@@ -295,7 +302,7 @@ void CompoundSprite::redraw() const
int amask = 0xff000000;
#endif
- SDL_Surface *surface = SDL_CreateRGBSurface(SDL_HWSURFACE, mWidth, mHeight,
+ SDL_Surface *surface = SDL_CreateRGBSurface(0, mWidth, mHeight,
32, rmask, gmask, bmask, amask);
if (!surface)
@@ -322,7 +329,7 @@ void CompoundSprite::redraw() const
delete graphics;
- SDL_Surface *surfaceA = SDL_CreateRGBSurface(SDL_HWSURFACE, mWidth, mHeight,
+ SDL_Surface *surfaceA = SDL_CreateRGBSurface(0, mWidth, mHeight,
32, rmask, gmask, bmask, amask);
SDL_SetAlpha(surface, 0, SDL_ALPHA_OPAQUE);
@@ -338,4 +345,5 @@ void CompoundSprite::redraw() const
SDL_FreeSurface(surfaceA);
mNeedsRedraw = false;
+#endif
}
diff --git a/src/cpp0x_compat/cstdint b/src/cpp0x_compat/cstdint
deleted file mode 100644
index 05d56c6e..00000000
--- a/src/cpp0x_compat/cstdint
+++ /dev/null
@@ -1,10 +0,0 @@
-/*
- * Compatibility header used when the compiler doesn't support C++0x.
- *
- * While GCC 4.2.1 understands types like uint16_t by default, later versions
- * are more strict so here are some typedefs for types used in our code.
- */
-
-typedef unsigned char uint8_t;
-typedef unsigned short uint16_t;
-typedef unsigned int uint32_t;
diff --git a/src/event.cpp b/src/event.cpp
index 45e65fff..73099cc3 100644
--- a/src/event.cpp
+++ b/src/event.cpp
@@ -37,7 +37,7 @@ Event::~Event()
// Integers
-void Event::setInt(const std::string &key, int value) throw (BadEvent)
+void Event::setInt(const std::string &key, int value)
{
if (mData.find(key) != mData.end())
throw KEY_ALREADY_EXISTS;
@@ -45,7 +45,7 @@ void Event::setInt(const std::string &key, int value) throw (BadEvent)
mData[key] = new IntData(value);
}
-int Event::getInt(const std::string &key) const throw (BadEvent)
+int Event::getInt(const std::string &key) const
{
VariableMap::const_iterator it = mData.find(key);
if (it == mData.end())
@@ -66,7 +66,7 @@ bool Event::hasInt(const std::string &key) const
// Strings
-void Event::setString(const std::string &key, const std::string &value) throw (BadEvent)
+void Event::setString(const std::string &key, const std::string &value)
{
if (mData.find(key) != mData.end())
throw KEY_ALREADY_EXISTS;
@@ -74,7 +74,7 @@ void Event::setString(const std::string &key, const std::string &value) throw (B
mData[key] = new StringData(value);
}
-const std::string &Event::getString(const std::string &key) const throw (BadEvent)
+const std::string &Event::getString(const std::string &key) const
{
VariableMap::const_iterator it = mData.find(key);
if (it == mData.end())
@@ -96,7 +96,7 @@ bool Event::hasString(const std::string &key) const
// Floats
-void Event::setFloat(const std::string &key, double value) throw (BadEvent)
+void Event::setFloat(const std::string &key, double value)
{
if (mData.find(key) != mData.end())
throw KEY_ALREADY_EXISTS;
@@ -104,7 +104,7 @@ void Event::setFloat(const std::string &key, double value) throw (BadEvent)
mData[key] = new FloatData(value);
}
-double Event::getFloat(const std::string &key) const throw (BadEvent)
+double Event::getFloat(const std::string &key) const
{
VariableMap::const_iterator it = mData.find(key);
if (it == mData.end())
@@ -125,7 +125,7 @@ bool Event::hasFloat(const std::string &key) const
// Booleans
-void Event::setBool(const std::string &key, bool value) throw (BadEvent)
+void Event::setBool(const std::string &key, bool value)
{
if (mData.find(key) != mData.end())
throw KEY_ALREADY_EXISTS;
@@ -133,7 +133,7 @@ void Event::setBool(const std::string &key, bool value) throw (BadEvent)
mData[key] = new BoolData(value);
}
-bool Event::getBool(const std::string &key) const throw (BadEvent)
+bool Event::getBool(const std::string &key) const
{
VariableMap::const_iterator it = mData.find(key);
if (it == mData.end())
@@ -154,7 +154,7 @@ bool Event::hasBool(const std::string &key) const
// Items
-void Event::setItem(const std::string &key, Item *value) throw (BadEvent)
+void Event::setItem(const std::string &key, Item *value)
{
if (mData.find(key) != mData.end())
throw KEY_ALREADY_EXISTS;
@@ -162,7 +162,7 @@ void Event::setItem(const std::string &key, Item *value) throw (BadEvent)
mData[key] = new ItemData(value);
}
-Item *Event::getItem(const std::string &key) const throw (BadEvent)
+Item *Event::getItem(const std::string &key) const
{
VariableMap::const_iterator it = mData.find(key);
if (it == mData.end())
@@ -183,7 +183,7 @@ bool Event::hasItem(const std::string &key) const
// Actors
-void Event::setActor(const std::string &key, ActorSprite *value) throw (BadEvent)
+void Event::setActor(const std::string &key, ActorSprite *value)
{
if (mData.find(key) != mData.end())
throw KEY_ALREADY_EXISTS;
@@ -191,7 +191,7 @@ void Event::setActor(const std::string &key, ActorSprite *value) throw (BadEvent
mData[key] = new ActorData(value);
}
-ActorSprite *Event::getActor(const std::string &key) const throw (BadEvent)
+ActorSprite *Event::getActor(const std::string &key) const
{
VariableMap::const_iterator it = mData.find(key);
if (it == mData.end())
diff --git a/src/event.h b/src/event.h
index f33e4c70..b785b16f 100644
--- a/src/event.h
+++ b/src/event.h
@@ -132,12 +132,12 @@ public:
/**
* Sets the given variable to the given integer, if it isn't already set.
*/
- void setInt(const std::string &key, int value) throw (BadEvent);
+ void setInt(const std::string &key, int value);
/**
* Returns the given variable if it is set and an integer.
*/
- int getInt(const std::string &key) const throw (BadEvent);
+ int getInt(const std::string &key) const;
/**
* Returns the given variable if it is set and an integer, returning the
@@ -156,12 +156,12 @@ public:
/**
* Sets the given variable to the given string, if it isn't already set.
*/
- void setString(const std::string &key, const std::string &value) throw (BadEvent);
+ void setString(const std::string &key, const std::string &value);
/**
* Returns the given variable if it is set and a string.
*/
- const std::string &getString(const std::string &key) const throw (BadEvent);
+ const std::string &getString(const std::string &key) const;
/**
* Returns the given variable if it is set and a string, returning the
@@ -182,12 +182,12 @@ public:
* Sets the given variable to the given floating-point, if it isn't already
* set.
*/
- void setFloat(const std::string &key, double value) throw (BadEvent);
+ void setFloat(const std::string &key, double value);
/**
* Returns the given variable if it is set and a floating-point.
*/
- double getFloat(const std::string &key) const throw (BadEvent);
+ double getFloat(const std::string &key) const;
/**
* Returns the given variable if it is set and a floating-point, returning
@@ -206,12 +206,12 @@ public:
/**
* Sets the given variable to the given boolean, if it isn't already set.
*/
- void setBool(const std::string &key, bool value) throw (BadEvent);
+ void setBool(const std::string &key, bool value);
/**
* Returns the given variable if it is set and a boolean.
*/
- bool getBool(const std::string &key) const throw (BadEvent);
+ bool getBool(const std::string &key) const;
/**
* Returns the given variable if it is set and a boolean, returning the
@@ -230,12 +230,12 @@ public:
/**
* Sets the given variable to the given Item, if it isn't already set.
*/
- void setItem(const std::string &key, Item *value) throw (BadEvent);
+ void setItem(const std::string &key, Item *value);
/**
* Returns the given variable if it is set and an Item.
*/
- Item *getItem(const std::string &key) const throw (BadEvent);
+ Item *getItem(const std::string &key) const;
/**
* Returns the given variable if it is set and an Item, returning the
@@ -254,12 +254,12 @@ public:
/**
* Sets the given variable to the given actor, if it isn't already set.
*/
- void setActor(const std::string &key, ActorSprite *value) throw (BadEvent);
+ void setActor(const std::string &key, ActorSprite *value);
/**
* Returns the given variable if it is set and an actor.
*/
- ActorSprite *getActor(const std::string &key) const throw (BadEvent);
+ ActorSprite *getActor(const std::string &key) const;
/**
* Returns the given variable if it is set and an actor, returning the
diff --git a/src/game.cpp b/src/game.cpp
index 824eb7d1..5b78bdb5 100644
--- a/src/game.cpp
+++ b/src/game.cpp
@@ -42,7 +42,6 @@
#include "sound.h"
#include "gui/chatwindow.h"
-#include "gui/confirmdialog.h"
#include "gui/debugwindow.h"
#include "gui/equipmentwindow.h"
#include "gui/gui.h"
@@ -72,7 +71,6 @@
#include "gui/widgets/layout.h"
#include "net/gamehandler.h"
-#include "net/generalhandler.h"
#include "net/net.h"
#include "net/playerhandler.h"
@@ -403,10 +401,10 @@ void Game::handleInput()
{
bool used = false;
- if (event.type == SDL_VIDEORESIZE)
+ if (event.type == SDL_WINDOWEVENT && event.window.event == SDL_WINDOWEVENT_RESIZED)
{
// Let the client deal with this one (it'll pass down from there)
- Client::instance()->handleVideoResize(event.resize.w, event.resize.h);
+ Client::instance()->handleVideoResize(event.window.data1, event.window.data2);
}
// Keyboard events (for discontinuous keys)
else if (event.type == SDL_KEYDOWN)
diff --git a/src/graphics.cpp b/src/graphics.cpp
index 08b1b298..d5c1e1a0 100644
--- a/src/graphics.cpp
+++ b/src/graphics.cpp
@@ -19,8 +19,6 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-#include <cassert>
-
#include "graphics.h"
#include "log.h"
@@ -28,122 +26,96 @@
#include "utils/gettext.h"
-#include <SDL_gfxBlitFunc.h>
-#include <SDL/SDL_rotozoom.h>
-
-Graphics::Graphics():
- mWidth(0),
- mHeight(0),
- mScale(1),
- mBpp(0),
- mFullscreen(false),
- mHWAccel(false),
- mBlitMode(BLIT_NORMAL),
- mScreenSurface(0)
+#include <guichan/exception.hpp>
+
+Graphics::~Graphics()
{
- mTarget = 0;
+ _endDraw();
}
-Graphics::~Graphics()
+void Graphics::setTarget(SDL_Window *target)
{
_endDraw();
+
+ mTarget = target;
+
+ if (mTarget)
+ _beginDraw();
}
-bool Graphics::setVideoMode(int w, int h, int bpp, bool fs, bool hwaccel)
+bool Graphics::setVideoMode(int w, int h, bool fs)
{
logger->log("Setting video mode %dx%d %s",
w, h, fs ? "fullscreen" : "windowed");
- logger->log("Bits per pixel: %d", bpp);
-
- int displayFlags = SDL_ANYFORMAT;
+ int windowFlags = SDL_WINDOW_ALLOW_HIGHDPI;
if (fs)
- displayFlags |= SDL_FULLSCREEN;
+ windowFlags |= SDL_WINDOW_FULLSCREEN;
else
- displayFlags |= SDL_RESIZABLE;
+ windowFlags |= SDL_WINDOW_RESIZABLE;
- if (hwaccel)
- displayFlags |= SDL_HWSURFACE | SDL_DOUBLEBUF;
- else
- displayFlags |= SDL_SWSURFACE;
+ // TODO_SDL2: Support SDL_WINDOW_FULLSCREEN_DESKTOP
- SDL_FreeSurface(mTarget);
- mTarget = 0;
+ SDL_Window *window = nullptr;
+ SDL_Renderer *renderer = nullptr;
+ SDL_CreateWindowAndRenderer(w, h, windowFlags, &window, &renderer);
- // Calculate scaling factor
- mScale = std::max(w / 640, h / 360);
+ if (!window)
+ return false;
- mScreenSurface = SDL_SetVideoMode(w, h, bpp, displayFlags);
- const SDL_PixelFormat& fmt = *(mScreenSurface->format);
- setTarget(SDL_CreateRGBSurface(SDL_SWSURFACE,
- w / mScale, h / mScale,
- fmt.BitsPerPixel,
- fmt.Rmask, fmt.Gmask, fmt.Bmask, 0));
+ SDL_SetWindowMinimumSize(window, 640, 360);
+ SDL_SetRenderDrawBlendMode(renderer, SDL_BLENDMODE_BLEND);
- if (!mTarget)
- return false;
+ setTarget(window);
- mWidth = mTarget->w;
- mHeight = mTarget->h;
- mBpp = bpp;
+ mRenderer = renderer;
+ videoResized(w, h);
mFullscreen = fs;
- mHWAccel = hwaccel;
-
- char videoDriverName[64];
- if (SDL_VideoDriverName(videoDriverName, 64))
- logger->log("Using video driver: %s", videoDriverName);
+ if (const char *driver = SDL_GetCurrentVideoDriver())
+ logger->log("Using video driver: %s", driver);
else
- logger->log("Using video driver: unknown");
-
- const SDL_VideoInfo *vi = SDL_GetVideoInfo();
-
- logger->log("Possible to create hardware surfaces: %s",
- vi->hw_available ? "yes" : "no");
- logger->log("Window manager available: %s",
- vi->wm_available ? "yes" : "no");
- logger->log("Accelerated hardware to hardware blits: %s",
- vi->blit_hw ? "yes" : "no");
- logger->log("Accelerated hardware to hardware colorkey blits: %s",
- vi->blit_hw_CC ? "yes" : "no");
- logger->log("Accelerated hardware to hardware alpha blits: %s",
- vi->blit_hw_A ? "yes" : "no");
- logger->log("Accelerated software to hardware blits: %s",
- vi->blit_sw ? "yes" : "no");
- logger->log("Accelerated software to hardware colorkey blits: %s",
- vi->blit_sw_CC ? "yes" : "no");
- logger->log("Accelerated software to hardware alpha blits: %s",
- vi->blit_sw_A ? "yes" : "no");
- logger->log("Accelerated color fills: %s",
- vi->blit_fill ? "yes" : "no");
- logger->log("Available video memory: %d", vi->video_mem);
+ logger->log("Using video driver: not initialized");
+
+ SDL_RendererInfo info;
+
+ if (SDL_GetRendererInfo(mRenderer, &info) == 0) {
+ logger->log("Using renderer: %s", info.name);
+
+ logger->log("The renderer is a software fallback: %s",
+ (info.flags & SDL_RENDERER_SOFTWARE) ? "yes" : "no");
+ logger->log("The renderer is hardware accelerated: %s",
+ (info.flags & SDL_RENDERER_ACCELERATED) ? "yes" : "no");
+ logger->log("Vsync: %s",
+ (info.flags & SDL_RENDERER_PRESENTVSYNC) ? "on" : "off");
+ logger->log("Renderer supports rendering to texture: %s",
+ (info.flags & SDL_RENDERER_TARGETTEXTURE) ? "yes" : "no");
+ logger->log("Max texture size: %dx%d",
+ info.max_texture_width, info.max_texture_height);
+ }
return true;
}
-bool Graphics::changeVideoMode(int w, int h, int bpp, bool fs, bool hwaccel)
+bool Graphics::changeVideoMode(int w, int h, bool fs)
{
// Just return success if we're already in this mode
- if (mScreenSurface && mScreenSurface->w == w &&
- mScreenSurface->h == h &&
- mBpp == bpp &&
- mFullscreen == fs &&
- mHWAccel == hwaccel)
+ if (mWidth == w &&
+ mHeight == h &&
+ mFullscreen == fs)
return true;
_endDraw();
- bool success = setVideoMode(w, h, bpp, fs, hwaccel);
+ bool success = setVideoMode(w, h, fs);
- // If it didn't work, try to restore fallback resolution. If that doesn't
+ // If it didn't work, try to restore the previous mode. If that doesn't
// work either, we're in big trouble and bail out.
- if (!success)
- {
- if (!setVideoMode(640, 360, mBpp, mFullscreen, mHWAccel))
- {
+ if (!success) {
+ if (!setVideoMode(mWidth, mHeight, mFullscreen)) {
logger->error(_("Failed to change video mode and couldn't "
- "switch back to the fallback mode!"));
+ "switch back to the previous mode!"));
}
}
@@ -152,12 +124,36 @@ bool Graphics::changeVideoMode(int w, int h, int bpp, bool fs, bool hwaccel)
return success;
}
+void Graphics::videoResized(int w, int h)
+{
+ const int prevWidth = mWidth;
+ const int prevHeight = mHeight;
+
+ mScale = getScale(w, h);
+ mWidth = w / mScale;
+ mHeight = h / mScale;
+
+ if (mWidth != prevWidth || mHeight != prevHeight) {
+ if (mScreenTexture) {
+ SDL_DestroyTexture(mScreenTexture);
+ mScreenTexture = nullptr;
+ }
+
+ if (mScale > 1) {
+ auto pixelFormat = SDL_GetWindowPixelFormat(mTarget);
+ mScreenTexture = SDL_CreateTexture(mRenderer, pixelFormat, SDL_TEXTUREACCESS_TARGET, mWidth, mHeight);
+ }
+
+ SDL_SetRenderTarget(mRenderer, mScreenTexture);
+ }
+}
+
bool Graphics::drawImage(Image *image, int x, int y)
{
- if (image)
- return drawImage(image, 0, 0, x, y, image->mBounds.w, image->mBounds.h);
- else
+ if (!image)
return false;
+
+ return drawImage(image, 0, 0, x, y, image->mBounds.w, image->mBounds.h);
}
bool Graphics::drawRescaledImage(Image *image, int srcX, int srcY,
@@ -167,15 +163,7 @@ bool Graphics::drawRescaledImage(Image *image, int srcX, int srcY,
bool useColor)
{
// Check that preconditions for blitting are met.
- if (!mTarget || !image)
- return false;
- if (!image->mSDLSurface)
- return false;
-
- Image *tmpImage = image->SDLgetScaledImage(desiredWidth, desiredHeight);
- bool returnValue = false;
-
- if (!tmpImage)
+ if (!mTarget || !image || !image->mTexture)
return false;
dstX += mClipStack.top().xOffset;
@@ -188,78 +176,37 @@ bool Graphics::drawRescaledImage(Image *image, int srcX, int srcY,
SDL_Rect srcRect;
dstRect.x = dstX; dstRect.y = dstY;
srcRect.x = srcX; srcRect.y = srcY;
- srcRect.w = tmpImage->getWidth();
- srcRect.h = tmpImage->getHeight();
-
- returnValue = !(SDL_BlitSurface(tmpImage->mSDLSurface, &srcRect,
- mTarget, &dstRect) < 0);
-
- tmpImage->decRef(Resource::DeleteImmediately);
+ srcRect.w = width;
+ srcRect.h = height;
+ dstRect.w = desiredWidth;
+ dstRect.h = desiredHeight;
- return returnValue;
+ return !(SDL_RenderCopy(mRenderer, image->mTexture, &srcRect, &dstRect) < 0);
}
bool Graphics::drawImage(Image *image, int srcX, int srcY, int dstX, int dstY,
- int width, int height, bool)
+ int width, int height, bool useColor)
{
- // Check that preconditions for blitting are met.
- if (!mTarget || !image || !image->mSDLSurface)
+ if (!image)
return false;
- dstX += mClipStack.top().xOffset;
- dstY += mClipStack.top().yOffset;
-
- srcX += image->mBounds.x;
- srcY += image->mBounds.y;
-
- SDL_Rect dstRect;
- SDL_Rect srcRect;
- dstRect.x = dstX; dstRect.y = dstY;
- srcRect.x = srcX; srcRect.y = srcY;
- srcRect.w = width;
- srcRect.h = height;
-
- if (mBlitMode == BLIT_NORMAL)
- return !(SDL_BlitSurface(image->mSDLSurface, &srcRect, mTarget, &dstRect) < 0);
- else
- return !(SDL_gfxBlitRGBA(image->mSDLSurface, &srcRect, mTarget, &dstRect) < 0);
+ return drawRescaledImage(image,
+ srcX, srcY,
+ dstX, dstY,
+ width, height,
+ width, height, useColor);
}
void Graphics::drawImagePattern(Image *image, int x, int y, int w, int h)
{
// Check that preconditions for blitting are met.
- if (!mTarget || !image)
- return;
- if (!image->mSDLSurface)
+ if (!image)
return;
const int iw = image->getWidth();
const int ih = image->getHeight();
- if (iw == 0 || ih == 0)
- return;
-
- for (int py = 0; py < h; py += ih) // Y position on pattern plane
- {
- int dh = (py + ih >= h) ? h - py : ih;
- int srcY = image->mBounds.y;
- int dstY = y + py + mClipStack.top().yOffset;
-
- for (int px = 0; px < w; px += iw) // X position on pattern plane
- {
- int dw = (px + iw >= w) ? w - px : iw;
- int srcX = image->mBounds.x;
- int dstX = x + px + mClipStack.top().xOffset;
-
- SDL_Rect dstRect;
- SDL_Rect srcRect;
- dstRect.x = dstX; dstRect.y = dstY;
- srcRect.x = srcX; srcRect.y = srcY;
- srcRect.w = dw; srcRect.h = dh;
-
- SDL_BlitSurface(image->mSDLSurface, &srcRect, mTarget, &dstRect);
- }
- }
+ drawRescaledImagePattern(image, x, y, w, h, iw, ih);
}
void Graphics::drawRescaledImagePattern(Image *image,
@@ -268,50 +215,34 @@ void Graphics::drawRescaledImagePattern(Image *image,
int scaledWidth, int scaledHeight)
{
// Check that preconditions for blitting are met.
- if (!mTarget || !image)
- return;
- if (!image->mSDLSurface)
+ if (!mTarget || !image || !image->mTexture)
return;
if (scaledHeight == 0 || scaledWidth == 0)
return;
- Image *tmpImage = image->SDLgetScaledImage(scaledWidth, scaledHeight);
- if (!tmpImage)
- return;
-
- const int iw = tmpImage->getWidth();
- const int ih = tmpImage->getHeight();
-
- if (iw == 0 || ih == 0)
- {
- tmpImage->decRef(Resource::DeleteImmediately);
- return;
- }
-
- for (int py = 0; py < h; py += ih) // Y position on pattern plane
+ for (int py = 0; py < h; py += scaledHeight) // Y position on pattern plane
{
- int dh = (py + ih >= h) ? h - py : ih;
- int srcY = tmpImage->mBounds.y;
+ int dh = (py + scaledHeight >= h) ? h - py : scaledHeight;
+ int srcY = image->mBounds.y;
int dstY = y + py + mClipStack.top().yOffset;
- for (int px = 0; px < w; px += iw) // X position on pattern plane
+ for (int px = 0; px < w; px += scaledWidth) // X position on pattern plane
{
- int dw = (px + iw >= w) ? w - px : iw;
- int srcX = tmpImage->mBounds.x;
+ int dw = (px + scaledWidth >= w) ? w - px : scaledWidth;
+ int srcX = image->mBounds.x;
int dstX = x + px + mClipStack.top().xOffset;
SDL_Rect dstRect;
SDL_Rect srcRect;
dstRect.x = dstX; dstRect.y = dstY;
+ dstRect.w = dw; dstRect.h = dh;
srcRect.x = srcX; srcRect.y = srcY;
srcRect.w = dw; srcRect.h = dh;
- SDL_BlitSurface(tmpImage->mSDLSurface, &srcRect, mTarget, &dstRect);
+ SDL_RenderCopy(mRenderer, image->mTexture, &srcRect, &dstRect);
}
}
-
- tmpImage->decRef(Resource::DeleteImmediately);
}
void Graphics::drawImageRect(int x, int y, int w, int h,
@@ -368,27 +299,16 @@ void Graphics::drawImageRect(int x, int y, int w, int h,
void Graphics::updateScreen()
{
- // Center viewport
- SDL_Rect dstRect;
- dstRect.x = (mScreenSurface->w-getWidth() * mScale) / 2;
- dstRect.y = (mScreenSurface->h-getHeight() * mScale) / 2;
-
- // Zoom in if necessary
- if (mScale > 1)
- {
- SDL_Surface *tmp = zoomSurface(mTarget, mScale, mScale, 0);
-
- // Copy temporary surface to screen
- SDL_BlitSurface(tmp, NULL, mScreenSurface, &dstRect);
- SDL_FreeSurface(tmp);
+ if (!mScreenTexture) {
+ // Simple case when we're rendering directly to the window
+ SDL_RenderPresent(mRenderer);
+ } else {
+ // Otherwise, we now render the screen surface to the window
+ SDL_SetRenderTarget(mRenderer, NULL);
+ SDL_RenderCopy(mRenderer, mScreenTexture, NULL, NULL);
+ SDL_RenderPresent(mRenderer);
+ SDL_SetRenderTarget(mRenderer, mScreenTexture);
}
- else
- {
- // Copy mTarget directly to screen
- SDL_BlitSurface(mTarget, NULL, mScreenSurface, &dstRect);
- }
-
- SDL_Flip(mScreenSurface);
}
SDL_Surface *Graphics::getScreenshot()
@@ -404,10 +324,145 @@ SDL_Surface *Graphics::getScreenshot()
#endif
int amask = 0x00000000;
- SDL_Surface *screenshot = SDL_CreateRGBSurface(SDL_SWSURFACE, mTarget->w,
- mTarget->h, 24, rmask, gmask, bmask, amask);
-
- SDL_BlitSurface(mTarget, NULL, screenshot, NULL);
+ SDL_Surface *screenshot = SDL_CreateRGBSurface(0, mWidth,
+ mHeight, 24, rmask, gmask, bmask, amask);
+ SDL_RenderReadPixels(mRenderer, NULL, SDL_PIXELFORMAT_RGB888, screenshot->pixels, screenshot->pitch);
return screenshot;
}
+
+bool Graphics::pushClipArea(gcn::Rectangle area)
+{
+ bool result = gcn::Graphics::pushClipArea(area);
+ updateSDLClipRect();
+ return result;
+}
+
+void Graphics::popClipArea()
+{
+ gcn::Graphics::popClipArea();
+ updateSDLClipRect();
+}
+
+void Graphics::updateSDLClipRect()
+{
+ if (mClipStack.empty())
+ {
+ SDL_RenderSetClipRect(mRenderer, NULL);
+ return;
+ }
+
+ const gcn::ClipRectangle &carea = mClipStack.top();
+ SDL_Rect rect;
+ rect.x = carea.x;
+ rect.y = carea.y;
+ rect.w = carea.width;
+ rect.h = carea.height;
+
+ SDL_RenderSetClipRect(mRenderer, &rect);
+}
+
+int Graphics::getScale(int w, int h)
+{
+ return std::max(w / 640, h / 360);
+}
+
+void Graphics::drawPoint(int x, int y)
+{
+ if (mClipStack.empty())
+ {
+ throw GCN_EXCEPTION("Clip stack is empty, perhaps you called a draw funtion outside of _beginDraw() and _endDraw()?");
+ }
+
+ const gcn::ClipRectangle &top = mClipStack.top();
+
+ x += top.xOffset;
+ y += top.yOffset;
+
+ if (!top.isPointInRect(x, y))
+ return;
+
+ SDL_SetRenderDrawColor(mRenderer,
+ (Uint8)(mColor.r),
+ (Uint8)(mColor.g),
+ (Uint8)(mColor.b),
+ (Uint8)(mColor.a));
+ SDL_RenderDrawPoint(mRenderer, x, y);
+}
+
+void Graphics::drawLine(int x1, int y1, int x2, int y2)
+{
+ if (mClipStack.empty())
+ {
+ throw GCN_EXCEPTION("Clip stack is empty, perhaps you called a draw funtion outside of _beginDraw() and _endDraw()?");
+ }
+
+ const gcn::ClipRectangle &top = mClipStack.top();
+
+ x1 += top.xOffset;
+ y1 += top.yOffset;
+ x2 += top.xOffset;
+ y2 += top.yOffset;
+
+ SDL_SetRenderDrawColor(mRenderer,
+ (Uint8)(mColor.r),
+ (Uint8)(mColor.g),
+ (Uint8)(mColor.b),
+ (Uint8)(mColor.a));
+ SDL_RenderDrawLine(mRenderer, x1, y1, x2, y2);
+}
+
+void Graphics::drawRectangle(const gcn::Rectangle &rectangle)
+{
+ if (mClipStack.empty())
+ {
+ throw GCN_EXCEPTION("Clip stack is empty, perhaps you called a draw funtion outside of _beginDraw() and _endDraw()?");
+ }
+
+ const gcn::ClipRectangle &top = mClipStack.top();
+
+ SDL_Rect rect;
+ rect.x = rectangle.x + top.xOffset;
+ rect.y = rectangle.y + top.yOffset;
+ rect.w = rectangle.width;
+ rect.h = rectangle.height;
+
+ SDL_SetRenderDrawColor(mRenderer,
+ (Uint8)(mColor.r),
+ (Uint8)(mColor.g),
+ (Uint8)(mColor.b),
+ (Uint8)(mColor.a));
+ SDL_RenderDrawRect(mRenderer, &rect);
+}
+
+void Graphics::fillRectangle(const gcn::Rectangle &rectangle)
+{
+ if (mClipStack.empty())
+ {
+ throw GCN_EXCEPTION("Clip stack is empty, perhaps you called a draw funtion outside of _beginDraw() and _endDraw()?");
+ }
+
+ const gcn::ClipRectangle &top = mClipStack.top();
+
+ gcn::Rectangle area = rectangle;
+ area.x += top.xOffset;
+ area.y += top.yOffset;
+
+ if(!area.isIntersecting(top))
+ {
+ return;
+ }
+
+ SDL_Rect rect;
+ rect.x = area.x;
+ rect.y = area.y;
+ rect.w = area.width;
+ rect.h = area.height;
+
+ SDL_SetRenderDrawColor(mRenderer,
+ (Uint8)(mColor.r),
+ (Uint8)(mColor.g),
+ (Uint8)(mColor.b),
+ (Uint8)(mColor.a));
+ SDL_RenderFillRect(mRenderer, &rect);
+}
diff --git a/src/graphics.h b/src/graphics.h
index 36a9adb9..f92374ec 100644
--- a/src/graphics.h
+++ b/src/graphics.h
@@ -22,13 +22,14 @@
#ifndef GRAPHICS_H
#define GRAPHICS_H
-#include <guichan/sdl/sdlgraphics.hpp>
+#include <SDL.h>
+
+#include <guichan/color.hpp>
+#include <guichan/graphics.hpp>
class Image;
class ImageRect;
-struct SDL_Surface;
-
static const int defaultScreenWidth = 800;
static const int defaultScreenHeight = 600;
@@ -49,8 +50,9 @@ static const int defaultScreenHeight = 600;
* Sections 0, 2, 6 and 8 will remain as is. 1, 3, 4, 5 and 7 will be
* repeated to fit the size of the widget.
*/
-struct ImageRect
+class ImageRect
{
+public:
enum ImagePosition
{
UPPER_LEFT = 0,
@@ -70,28 +72,36 @@ struct ImageRect
/**
* A central point of control for graphics.
*/
-class Graphics : public gcn::SDLGraphics
+class Graphics : public gcn::Graphics
{
public:
- enum BlitMode {
- BLIT_NORMAL = 0,
- BLIT_GFX
- };
-
- Graphics();
+ Graphics() = default;
virtual ~Graphics();
/**
+ * Sets the target SDL_Window to draw to. This funtion also pushes a
+ * clip areas corresponding to the dimension of the target.
+ *
+ * @param target the target to draw to.
+ */
+ virtual void setTarget(SDL_Window *target);
+
+ SDL_Window *getTarget() const { return mTarget; }
+ SDL_Renderer *getRenderer() const { return mRenderer; }
+
+ /**
* Try to create a window with the given settings.
*/
- virtual bool setVideoMode(int w, int h, int bpp, bool fs, bool hwaccel);
+ virtual bool setVideoMode(int w, int h, bool fs);
/**
* Change the video mode. Can be used for switching to full screen,
* changing resolution or adapting after window resize.
*/
- bool changeVideoMode(int w, int h, int bpp, bool fs, bool hwaccel);
+ bool changeVideoMode(int w, int h, bool fs);
+
+ virtual void videoResized(int w, int h);
/**
* Blits an image onto the screen.
@@ -176,12 +186,6 @@ class Graphics : public gcn::SDLGraphics
drawImageRect(area.x, area.y, area.width, area.height, imgRect);
}
- void setBlitMode(BlitMode mode)
- { mBlitMode = mode; }
-
- BlitMode getBlitMode()
- { return mBlitMode; }
-
/**
* Updates the screen. This is done by either copying the buffer to the
* screen or swapping pages.
@@ -189,12 +193,12 @@ class Graphics : public gcn::SDLGraphics
virtual void updateScreen();
/**
- * Returns the width of the drawable surface.
+ * Returns the width of the screen.
*/
int getWidth() const { return mWidth; }
/**
- * Returns the height of the drawable surface.
+ * Returns the height of the screen.
*/
int getHeight() const { return mHeight; }
@@ -204,38 +208,60 @@ class Graphics : public gcn::SDLGraphics
int getScale() const { return mScale; }
/**
- * Returns the amount of bits per pixel that was requested (not the
- * actual amount that's currently active).
- */
- int getBpp() const { return mBpp; }
-
- /**
* Returns whether we're in a full screen mode.
*/
bool getFullscreen() const { return mFullscreen; }
/**
- * Returns whether old-fashioned SDL-based hardware acceleration was
- * requested (not whether it's currently active).
- */
- bool getHWAccel() const { return mHWAccel; }
-
- /**
* Takes a screenshot and returns it as SDL surface.
*/
virtual SDL_Surface *getScreenshot();
gcn::Font *getFont() const { return mFont; }
+ virtual bool pushClipArea(gcn::Rectangle area);
+
+ virtual void popClipArea();
+
+ virtual void drawImage(const gcn::Image *image,
+ int srcX,
+ int srcY,
+ int dstX,
+ int dstY,
+ int width,
+ int height) {} // not used
+
+ virtual void drawPoint(int x, int y);
+
+ virtual void drawLine(int x1, int y1, int x2, int y2);
+
+ virtual void drawRectangle(const gcn::Rectangle &rectangle);
+
+ virtual void fillRectangle(const gcn::Rectangle &rectangle);
+
+ virtual void setColor(const gcn::Color &color)
+ {
+ mColor = color;
+ }
+
+ virtual const gcn::Color &getColor() const
+ {
+ return mColor;
+ }
+
protected:
- int mWidth;
- int mHeight;
- int mScale;
- int mBpp;
- bool mFullscreen;
- bool mHWAccel;
- BlitMode mBlitMode;
- SDL_Surface *mScreenSurface;
+ void updateSDLClipRect();
+ int getScale(int w, int h);
+
+ int mWidth = 0;
+ int mHeight = 0;
+ int mScale = 1;
+ bool mFullscreen = false;
+ gcn::Color mColor;
+
+ SDL_Window *mTarget = nullptr;
+ SDL_Renderer *mRenderer = nullptr;
+ SDL_Texture *mScreenTexture = nullptr;
};
extern Graphics *graphics;
diff --git a/src/gui/gui.cpp b/src/gui/gui.cpp
index 2e1d006e..cb6682bd 100644
--- a/src/gui/gui.cpp
+++ b/src/gui/gui.cpp
@@ -26,6 +26,7 @@
#include "gui/sdlinput.h"
#include "gui/truetypefont.h"
+#include "gui/widgets/textfield.h"
#include "gui/widgets/window.h"
#include "gui/widgets/windowcontainer.h"
@@ -190,6 +191,12 @@ void Gui::logic()
Palette::advanceGradients();
gcn::Gui::logic();
+
+ while (!guiInput->isTextQueueEmpty())
+ {
+ TextInput textInput = guiInput->dequeueTextInput();
+ handleTextInput(textInput);
+ }
}
void Gui::draw()
@@ -267,3 +274,14 @@ void Gui::handleMouseMoved(const gcn::MouseInput &mouseInput)
gcn::Gui::handleMouseMoved(mouseInput);
mMouseInactivityTimer = 0;
}
+
+void Gui::handleTextInput(const TextInput &textInput)
+{
+ if (auto focused = mFocusHandler->getFocused())
+ {
+ if (auto textField = dynamic_cast<TextField*>(focused))
+ {
+ textField->textInput(textInput);
+ }
+ }
+}
diff --git a/src/gui/gui.h b/src/gui/gui.h
index 006987da..998b6ec8 100644
--- a/src/gui/gui.h
+++ b/src/gui/gui.h
@@ -26,6 +26,7 @@
#include <guichan/gui.hpp>
+class TextInput;
class Graphics;
class GuiConfigListener;
class ImageSet;
@@ -114,6 +115,7 @@ class Gui : public gcn::Gui
protected:
void handleMouseMoved(const gcn::MouseInput &mouseInput);
+ void handleTextInput(const TextInput &textInput);
private:
GuiConfigListener *mConfigListener;
diff --git a/src/gui/sdlinput.cpp b/src/gui/sdlinput.cpp
index 46636d52..c0f24a7a 100644
--- a/src/gui/sdlinput.cpp
+++ b/src/gui/sdlinput.cpp
@@ -109,6 +109,23 @@ gcn::MouseInput SDLInput::dequeueMouseInput()
return mouseInput;
}
+bool SDLInput::isTextQueueEmpty() const
+{
+ return mTextInputQueue.empty();
+}
+
+TextInput SDLInput::dequeueTextInput()
+{
+ if (mTextInputQueue.empty())
+ {
+ throw GCN_EXCEPTION("The queue is empty.");
+ }
+
+ TextInput textInput(mTextInputQueue.front());
+ mTextInputQueue.pop();
+ return textInput;
+}
+
void SDLInput::pushInput(SDL_Event event)
{
gcn::KeyInput keyInput;
@@ -122,8 +139,8 @@ void SDLInput::pushInput(SDL_Event event)
keyInput.setShiftPressed(event.key.keysym.mod & KMOD_SHIFT);
keyInput.setControlPressed(event.key.keysym.mod & KMOD_CTRL);
keyInput.setAltPressed(event.key.keysym.mod & KMOD_ALT);
- keyInput.setMetaPressed(event.key.keysym.mod & KMOD_META);
- keyInput.setNumericPad(event.key.keysym.sym >= SDLK_KP0
+ keyInput.setMetaPressed(event.key.keysym.mod & KMOD_GUI);
+ keyInput.setNumericPad(event.key.keysym.sym >= SDLK_KP_0
&& event.key.keysym.sym <= SDLK_KP_EQUALS);
mKeyInputQueue.push(keyInput);
@@ -135,8 +152,8 @@ void SDLInput::pushInput(SDL_Event event)
keyInput.setShiftPressed(event.key.keysym.mod & KMOD_SHIFT);
keyInput.setControlPressed(event.key.keysym.mod & KMOD_CTRL);
keyInput.setAltPressed(event.key.keysym.mod & KMOD_ALT);
- keyInput.setMetaPressed(event.key.keysym.mod & KMOD_META);
- keyInput.setNumericPad(event.key.keysym.sym >= SDLK_KP0
+ keyInput.setMetaPressed(event.key.keysym.mod & KMOD_GUI);
+ keyInput.setNumericPad(event.key.keysym.sym >= SDLK_KP_0
&& event.key.keysym.sym <= SDLK_KP_EQUALS);
mKeyInputQueue.push(keyInput);
@@ -147,19 +164,7 @@ void SDLInput::pushInput(SDL_Event event)
mouseInput.setX(event.button.x);
mouseInput.setY(event.button.y);
mouseInput.setButton(convertMouseButton(event.button.button));
-
- if (event.button.button == SDL_BUTTON_WHEELDOWN)
- {
- mouseInput.setType(gcn::MouseInput::WHEEL_MOVED_DOWN);
- }
- else if (event.button.button == SDL_BUTTON_WHEELUP)
- {
- mouseInput.setType(gcn::MouseInput::WHEEL_MOVED_UP);
- }
- else
- {
- mouseInput.setType(gcn::MouseInput::PRESSED);
- }
+ mouseInput.setType(gcn::MouseInput::PRESSED);
mouseInput.setTimeStamp(SDL_GetTicks());
mMouseInputQueue.push(mouseInput);
break;
@@ -183,6 +188,35 @@ void SDLInput::pushInput(SDL_Event event)
mMouseInputQueue.push(mouseInput);
break;
+ case SDL_MOUSEWHEEL:
+ if (event.wheel.y) {
+#if SDL_VERSION_ATLEAST(2, 26, 0)
+ mouseInput.setX(event.wheel.mouseX);
+ mouseInput.setY(event.wheel.mouseY);
+#else
+ int x, y;
+ SDL_GetMouseState(&x, &y);
+ mouseInput.setX(x);
+ mouseInput.setY(y);
+#endif
+ mouseInput.setButton(gcn::MouseInput::EMPTY);
+ mouseInput.setType(event.wheel.y > 0 ? gcn::MouseInput::WHEEL_MOVED_UP
+ : gcn::MouseInput::WHEEL_MOVED_DOWN);
+ mouseInput.setTimeStamp(SDL_GetTicks());
+ mMouseInputQueue.push(mouseInput);
+ }
+ break;
+
+ case SDL_TEXTINPUT:
+ mTextInputQueue.emplace(event.text.text);
+ break;
+
+ // TODO_SDL2: This is now a window event
+ // case SDL_WINDOWEVENT:
+ // switch (event.window.event) {
+ // }
+ // break;
+#if 0
case SDL_ACTIVEEVENT:
/*
* This occurs when the mouse leaves the window and the Gui-chan
@@ -209,7 +243,7 @@ void SDLInput::pushInput(SDL_Event event)
mMouseInWindow = true;
}
break;
-
+#endif
} // end switch
}
@@ -231,9 +265,9 @@ int SDLInput::convertMouseButton(int button)
int SDLInput::convertKeyCharacter(SDL_Event event)
{
- SDL_keysym keysym = event.key.keysym;
+ SDL_Keysym keysym = event.key.keysym;
- int value = keysym.unicode;
+ int value = keysym.sym;
switch (keysym.sym)
{
@@ -265,16 +299,10 @@ int SDLInput::convertKeyCharacter(SDL_Event event)
value = Key::PAUSE;
break;
case SDLK_SPACE:
- // Special characters like ~ (tilde) ends up
- // with the keysym.sym SDLK_SPACE which
- // without this check would be lost. The check
- // is only valid on key down events in SDL.
- if (event.type == SDL_KEYUP || keysym.unicode == ' ')
- {
- value = Key::SPACE;
- }
+ value = Key::SPACE;
break;
case SDLK_ESCAPE:
+ case SDLK_AC_BACK:
value = Key::ESCAPE;
break;
case SDLK_DELETE:
@@ -292,7 +320,7 @@ int SDLInput::convertKeyCharacter(SDL_Event event)
case SDLK_PAGEUP:
value = Key::PAGE_UP;
break;
- case SDLK_PRINT:
+ case SDLK_PRINTSCREEN:
value = Key::PRINT_SCREEN;
break;
case SDLK_PAGEDOWN:
@@ -343,27 +371,21 @@ int SDLInput::convertKeyCharacter(SDL_Event event)
case SDLK_F15:
value = Key::F15;
break;
- case SDLK_NUMLOCK:
+ case SDLK_NUMLOCKCLEAR:
value = Key::NUM_LOCK;
break;
case SDLK_CAPSLOCK:
value = Key::CAPS_LOCK;
break;
- case SDLK_SCROLLOCK:
+ case SDLK_SCROLLLOCK:
value = Key::SCROLL_LOCK;
break;
- case SDLK_RMETA:
+ case SDLK_RGUI:
value = Key::RIGHT_META;
break;
- case SDLK_LMETA:
+ case SDLK_LGUI:
value = Key::LEFT_META;
break;
- case SDLK_LSUPER:
- value = Key::LEFT_SUPER;
- break;
- case SDLK_RSUPER:
- value = Key::RIGHT_SUPER;
- break;
case SDLK_MODE:
value = Key::ALT_GR;
break;
@@ -394,34 +416,34 @@ int SDLInput::convertKeyCharacter(SDL_Event event)
{
switch (keysym.sym)
{
- case SDLK_KP0:
+ case SDLK_KP_0:
value = Key::INSERT;
break;
- case SDLK_KP1:
+ case SDLK_KP_1:
value = Key::END;
break;
- case SDLK_KP2:
+ case SDLK_KP_2:
value = Key::DOWN;
break;
- case SDLK_KP3:
+ case SDLK_KP_3:
value = Key::PAGE_DOWN;
break;
- case SDLK_KP4:
+ case SDLK_KP_4:
value = Key::LEFT;
break;
- case SDLK_KP5:
+ case SDLK_KP_5:
value = 0;
break;
- case SDLK_KP6:
+ case SDLK_KP_6:
value = Key::RIGHT;
break;
- case SDLK_KP7:
+ case SDLK_KP_7:
value = Key::HOME;
break;
- case SDLK_KP8:
+ case SDLK_KP_8:
value = Key::UP;
break;
- case SDLK_KP9:
+ case SDLK_KP_9:
value = Key::PAGE_UP;
break;
default:
diff --git a/src/gui/sdlinput.h b/src/gui/sdlinput.h
index 90f70df3..09bb788e 100644
--- a/src/gui/sdlinput.h
+++ b/src/gui/sdlinput.h
@@ -61,13 +61,15 @@
#include <queue>
-#include <SDL/SDL.h>
+#include <SDL.h>
#include <guichan/input.hpp>
#include <guichan/keyinput.hpp>
#include <guichan/mouseinput.hpp>
#include <guichan/platform.hpp>
+#include <string>
+
namespace Key
{
enum
@@ -122,6 +124,19 @@ namespace Key
};
}
+class TextInput
+{
+public:
+ TextInput(const char *text)
+ : mText(text)
+ {}
+
+ const std::string &getText() const { return mText; }
+
+private:
+ std::string mText;
+};
+
/**
* SDL implementation of Input.
*/
@@ -160,6 +175,10 @@ public:
virtual gcn::MouseInput dequeueMouseInput();
+ bool isTextQueueEmpty() const;
+
+ TextInput dequeueTextInput();
+
protected:
/**
* Converts a mouse button from SDL to a Guichan mouse button
@@ -181,6 +200,7 @@ protected:
std::queue<gcn::KeyInput> mKeyInputQueue;
std::queue<gcn::MouseInput> mMouseInputQueue;
+ std::queue<TextInput> mTextInputQueue;
bool mMouseDown;
bool mMouseInWindow;
diff --git a/src/gui/setup.cpp b/src/gui/setup.cpp
index c468490c..eb59c4ea 100644
--- a/src/gui/setup.cpp
+++ b/src/gui/setup.cpp
@@ -38,6 +38,8 @@
#include "utils/dtor.h"
#include "utils/gettext.h"
+#include <functional>
+
extern Window *statusWindow;
Setup::Setup():
@@ -103,12 +105,12 @@ void Setup::action(const gcn::ActionEvent &event)
if (event.getId() == "Apply")
{
setVisible(false);
- for_each(mTabs.begin(), mTabs.end(), std::mem_fun(&SetupTab::apply));
+ for_each(mTabs.begin(), mTabs.end(), std::mem_fn(&SetupTab::apply));
}
else if (event.getId() == "Cancel")
{
setVisible(false);
- for_each(mTabs.begin(), mTabs.end(), std::mem_fun(&SetupTab::cancel));
+ for_each(mTabs.begin(), mTabs.end(), std::mem_fn(&SetupTab::cancel));
}
else if (event.getId() == "Reset Windows")
{
diff --git a/src/gui/setup_keyboard.cpp b/src/gui/setup_keyboard.cpp
index 5e29519b..b66ba3aa 100644
--- a/src/gui/setup_keyboard.cpp
+++ b/src/gui/setup_keyboard.cpp
@@ -178,8 +178,8 @@ void Setup_Keyboard::refreshAssignedKey(int index)
caption = keyboard.getKeyCaption(index) + ": ";
else
{
- char *temp = SDL_GetKeyName(
- (SDLKey) keyboard.getKeyValue(index));
+ const char *temp = SDL_GetKeyName(
+ (SDL_Scancode) keyboard.getKeyValue(index));
caption = strprintf("%-25s",
(keyboard.getKeyCaption(index) + ": ").c_str()) + toString(temp);
diff --git a/src/gui/setup_video.cpp b/src/gui/setup_video.cpp
index 5a697160..ac419de5 100644
--- a/src/gui/setup_video.cpp
+++ b/src/gui/setup_video.cpp
@@ -26,8 +26,6 @@
#include "game.h"
#include "graphics.h"
#include "localplayer.h"
-#include "log.h"
-#include "main.h"
#include "gui/okdialog.h"
@@ -38,8 +36,6 @@
#include "gui/widgets/scrollarea.h"
#include "gui/widgets/slider.h"
#include "gui/widgets/spacer.h"
-#include "gui/widgets/textfield.h"
-#include "gui/widgets/dropdown.h"
#include "utils/gettext.h"
#include "utils/stringutils.h"
@@ -90,26 +86,21 @@ class ModeListModel : public gcn::ListModel
ModeListModel::ModeListModel()
{
/* Get available fullscreen/hardware modes */
- SDL_Rect **modes = SDL_ListModes(NULL, SDL_FULLSCREEN | SDL_HWSURFACE);
-
- /* Check which modes are available */
- if (modes == (SDL_Rect **)0)
- logger->log("No modes available");
- else if (modes == (SDL_Rect **)-1)
- logger->log("All resolutions available");
- else
+ const int numModes = SDL_GetNumDisplayModes(0);
+ for (int i = 0; i < numModes; i++)
{
- for (int i = 0; modes[i]; ++i)
- {
- const int width = modes[i]->w;
- const int height = modes[i]->h;
+ SDL_DisplayMode mode;
+ if (SDL_GetDisplayMode(0, i, &mode) != 0)
+ continue;
- // Skip the unreasonably small modes
- if (width < 640 || height < 360)
- continue;
+ // Skip the unreasonably small modes
+ if (mode.w < 640 || mode.h < 360)
+ continue;
- mVideoModes.push_back(toString(width) + "x" + toString(height));
- }
+ // TODO_SDL2: Modes now dinstinguish between pixel format and refresh rate as well
+ // TODO_SDL2: Fullscreen mode needs display selection
+
+ mVideoModes.push_back(toString(mode.w) + "x" + toString(mode.h));
}
}
@@ -255,9 +246,7 @@ void Setup_Video::apply()
{
if (!graphics->changeVideoMode(screenWidth,
screenHeight,
- graphics->getBpp(),
- fullscreen,
- graphics->getHWAccel()))
+ fullscreen))
{
std::stringstream errorMessage;
if (fullscreen)
diff --git a/src/gui/socialwindow.cpp b/src/gui/socialwindow.cpp
index 1b960d64..437f9d01 100644
--- a/src/gui/socialwindow.cpp
+++ b/src/gui/socialwindow.cpp
@@ -33,8 +33,6 @@
#include "gui/widgets/avatarlistbox.h"
#include "gui/widgets/browserbox.h"
#include "gui/widgets/button.h"
-#include "gui/widgets/container.h"
-#include "gui/widgets/label.h"
#include "gui/widgets/linkhandler.h"
#include "gui/widgets/popup.h"
#include "gui/widgets/scrollarea.h"
@@ -47,7 +45,6 @@
#include "resources/theme.h"
-#include "utils/dtor.h"
#include "utils/gettext.h"
#include "utils/stringutils.h"
@@ -618,7 +615,7 @@ void SocialWindow::showPartyCreate()
{
new OkDialog(_("Create Party"),
_("Cannot create party. You are already in a party"),
- this);
+ true, this);
return;
}
diff --git a/src/gui/tradewindow.h b/src/gui/tradewindow.h
index 59ddcbdc..20da4574 100644
--- a/src/gui/tradewindow.h
+++ b/src/gui/tradewindow.h
@@ -117,7 +117,7 @@ class TradeWindow : public Window, gcn::ActionListener, gcn::SelectionListener
*/
void setStatus(Status s);
- typedef const std::auto_ptr<Inventory> InventoryPtr;
+ typedef const std::unique_ptr<Inventory> InventoryPtr;
InventoryPtr mMyInventory;
InventoryPtr mPartnerInventory;
diff --git a/src/gui/truetypefont.cpp b/src/gui/truetypefont.cpp
index 620ba191..443adaa5 100644
--- a/src/gui/truetypefont.cpp
+++ b/src/gui/truetypefont.cpp
@@ -28,6 +28,7 @@
#include "utils/stringutils.h"
+#include <guichan/color.hpp>
#include <guichan/exception.hpp>
const unsigned int CACHE_SIZE = 256;
@@ -53,9 +54,10 @@ class TextChunk
void generate(TTF_Font *font)
{
SDL_Color sdlCol;
- sdlCol.b = color.b;
sdlCol.r = color.r;
sdlCol.g = color.g;
+ sdlCol.b = color.b;
+ sdlCol.a = color.a;
const char *str = getSafeUtf8String(text);
SDL_Surface *surface = TTF_RenderUTF8_Blended(
diff --git a/src/gui/viewport.cpp b/src/gui/viewport.cpp
index 0f737fb0..b2945617 100644
--- a/src/gui/viewport.cpp
+++ b/src/gui/viewport.cpp
@@ -311,7 +311,7 @@ void Viewport::_followMouse()
if (mPlayerFollowMouse && button & SDL_BUTTON(1))
{
// We create a mouse event and send it to mouseDragged.
- Uint8 *keys = SDL_GetKeyState(NULL);
+ const Uint8 *keys = SDL_GetKeyboardState(NULL);
gcn::MouseEvent mouseEvent(NULL,
(keys[SDLK_LSHIFT] || keys[SDLK_RSHIFT]),
false,
diff --git a/src/gui/widgets/button.cpp b/src/gui/widgets/button.cpp
index 4a31fa63..9247f67a 100644
--- a/src/gui/widgets/button.cpp
+++ b/src/gui/widgets/button.cpp
@@ -182,7 +182,7 @@ Button::~Button()
{
for (int mode = 0; mode < BUTTON_COUNT; ++mode)
{
- for_each(mButton[mode].grid, mButton[mode].grid + 9,
+ std::for_each(mButton[mode].grid, mButton[mode].grid + 9,
dtor<Image*>());
}
delete[] mButton;
diff --git a/src/gui/widgets/desktop.cpp b/src/gui/widgets/desktop.cpp
index ec76f861..c9974fec 100644
--- a/src/gui/widgets/desktop.cpp
+++ b/src/gui/widgets/desktop.cpp
@@ -94,14 +94,9 @@ void Desktop::draw(gcn::Graphics *graphics)
if (mWallpaper)
{
- if (!Image::useOpenGL())
- g->drawImage(mWallpaper,
- (getWidth() - mWallpaper->getWidth()) / 2,
- (getHeight() - mWallpaper->getHeight()) / 2);
- else
- g->drawRescaledImage(mWallpaper, 0, 0, 0, 0,
- mWallpaper->getWidth(), mWallpaper->getHeight(),
- getWidth(), getHeight(), false);
+ g->drawRescaledImage(mWallpaper, 0, 0, 0, 0,
+ mWallpaper->getWidth(), mWallpaper->getHeight(),
+ getWidth(), getHeight(), false);
}
mBgSkin->setAlpha(1.0f);
@@ -168,19 +163,6 @@ void Desktop::setBestFittingWallpaper()
mWallpaper->decRef(Resource::DeleteImmediately);
mWallpaper = wallpaper;
-
- // In software mode we try to prescale the image for performance
- if (!wallpaper->useOpenGL() &&
- (wallpaper->getWidth() != width ||
- wallpaper->getHeight() != height))
- {
- if (Image *prescaled = wallpaper->SDLgetScaledImage(width, height))
- {
- // Make sure the original can be freed
- wallpaper->decRef();
- mWallpaper = prescaled;
- }
- }
}
else
{
diff --git a/src/gui/widgets/dropdown.cpp b/src/gui/widgets/dropdown.cpp
index e90f6073..101afaef 100644
--- a/src/gui/widgets/dropdown.cpp
+++ b/src/gui/widgets/dropdown.cpp
@@ -102,7 +102,7 @@ DropDown::~DropDown()
buttons[1][0]->decRef();
buttons[1][1]->decRef();
- for_each(skin.grid, skin.grid + 9, dtor<Image*>());
+ std::for_each(skin.grid, skin.grid + 9, dtor<Image*>());
}
delete mScrollArea;
diff --git a/src/gui/widgets/emoteshortcutcontainer.cpp b/src/gui/widgets/emoteshortcutcontainer.cpp
index 3105a762..cdb2d3c4 100644
--- a/src/gui/widgets/emoteshortcutcontainer.cpp
+++ b/src/gui/widgets/emoteshortcutcontainer.cpp
@@ -92,7 +92,7 @@ void EmoteShortcutContainer::draw(gcn::Graphics *graphics)
// Draw emote keyboard shortcut.
const char *key = SDL_GetKeyName(
- (SDLKey) keyboard.getKeyValue(keyboard.KEY_EMOTE_1 + i));
+ (SDL_Scancode) keyboard.getKeyValue(keyboard.KEY_EMOTE_1 + i));
graphics->setColor(Theme::getThemeColor(Theme::TEXT));
g->drawText(key, emoteX + 2, emoteY + 2, gcn::Graphics::LEFT);
diff --git a/src/gui/widgets/itemshortcutcontainer.cpp b/src/gui/widgets/itemshortcutcontainer.cpp
index f1690d43..396de3bd 100644
--- a/src/gui/widgets/itemshortcutcontainer.cpp
+++ b/src/gui/widgets/itemshortcutcontainer.cpp
@@ -86,7 +86,7 @@ void ItemShortcutContainer::draw(gcn::Graphics *graphics)
// Draw item keyboard shortcut.
const char *key = SDL_GetKeyName(
- (SDLKey) keyboard.getKeyValue(keyboard.KEY_SHORTCUT_1 + i));
+ (SDL_Scancode) keyboard.getKeyValue(keyboard.KEY_SHORTCUT_1 + i));
graphics->setColor(Theme::getThemeColor(Theme::TEXT));
g->drawText(key, itemX + 2, itemY + 2, gcn::Graphics::LEFT);
diff --git a/src/gui/widgets/playerbox.cpp b/src/gui/widgets/playerbox.cpp
index 5c5976c1..4f341af0 100644
--- a/src/gui/widgets/playerbox.cpp
+++ b/src/gui/widgets/playerbox.cpp
@@ -75,7 +75,7 @@ PlayerBox::~PlayerBox()
if (instances == 0)
{
- for_each(background.grid, background.grid + 9, dtor<Image*>());
+ std::for_each(background.grid, background.grid + 9, dtor<Image*>());
}
}
diff --git a/src/gui/widgets/progressbar.cpp b/src/gui/widgets/progressbar.cpp
index 27b194ff..4695f5ab 100644
--- a/src/gui/widgets/progressbar.cpp
+++ b/src/gui/widgets/progressbar.cpp
@@ -88,7 +88,7 @@ ProgressBar::~ProgressBar()
if (mInstances == 0)
{
- for_each(mBorder.grid, mBorder.grid + 9, dtor<Image*>());
+ std::for_each(mBorder.grid, mBorder.grid + 9, dtor<Image*>());
}
}
diff --git a/src/gui/widgets/scrollarea.cpp b/src/gui/widgets/scrollarea.cpp
index d5e824e1..c95adeaa 100644
--- a/src/gui/widgets/scrollarea.cpp
+++ b/src/gui/widgets/scrollarea.cpp
@@ -66,9 +66,9 @@ ScrollArea::~ScrollArea()
if (instances == 0)
{
- for_each(background.grid, background.grid + 9, dtor<Image*>());
- for_each(vMarker.grid, vMarker.grid + 9, dtor<Image*>());
- for_each(vMarkerHi.grid, vMarkerHi.grid + 9, dtor<Image*>());
+ std::for_each(background.grid, background.grid + 9, dtor<Image*>());
+ std::for_each(vMarker.grid, vMarker.grid + 9, dtor<Image*>());
+ std::for_each(vMarkerHi.grid, vMarkerHi.grid + 9, dtor<Image*>());
buttons[UP][0]->decRef();
buttons[UP][1]->decRef();
diff --git a/src/gui/widgets/tab.cpp b/src/gui/widgets/tab.cpp
index 17b7108f..c8ed2141 100644
--- a/src/gui/widgets/tab.cpp
+++ b/src/gui/widgets/tab.cpp
@@ -76,7 +76,7 @@ Tab::~Tab()
{
for (int mode = 0; mode < TAB_COUNT; mode++)
{
- for_each(tabImg[mode].grid, tabImg[mode].grid + 9, dtor<Image*>());
+ std::for_each(tabImg[mode].grid, tabImg[mode].grid + 9, dtor<Image*>());
}
}
}
diff --git a/src/gui/widgets/textfield.cpp b/src/gui/widgets/textfield.cpp
index ec57f1c7..35ce09c5 100644
--- a/src/gui/widgets/textfield.cpp
+++ b/src/gui/widgets/textfield.cpp
@@ -24,7 +24,6 @@
#include "configuration.h"
#include "graphics.h"
-#include "gui/palette.h"
#include "gui/sdlinput.h"
#include "resources/image.h"
@@ -36,6 +35,8 @@
#include <guichan/font.hpp>
+#include <SDL.h>
+
#undef DELETE //Win32 compatibility hack
int TextField::instances = 0;
@@ -84,7 +85,7 @@ TextField::~TextField()
instances--;
if (instances == 0)
- for_each(skin.grid, skin.grid + 9, dtor<Image*>());
+ std::for_each(skin.grid, skin.grid + 9, dtor<Image*>());
}
void TextField::updateAlpha()
@@ -162,33 +163,7 @@ int TextField::getValue() const
void TextField::keyPressed(gcn::KeyEvent &keyEvent)
{
- int val = keyEvent.getKey().getValue();
-
- if (val >= 32)
- {
- int l;
- if (val < 128) l = 1; // 0xxxxxxx
- else if (val < 0x800) l = 2; // 110xxxxx 10xxxxxx
- else if (val < 0x10000) l = 3; // 1110xxxx 10xxxxxx 10xxxxxx
- else l = 4; // 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx
-
- char buf[4];
- for (int i = 0; i < l; ++i)
- {
- buf[i] = val >> (6 * (l - i - 1));
- if (i > 0) buf[i] = (buf[i] & 63) | 128;
- }
-
- if (l > 1) buf[0] |= 255 << (8 - l);
-
- mText.insert(mCaretPosition, std::string(buf, buf + l));
- mCaretPosition += l;
- }
-
- /* In UTF-8, 10xxxxxx is only used for inner parts of characters. So skip
- them when processing key presses. */
-
- switch (val)
+ switch (keyEvent.getKey().getValue())
{
case Key::LEFT:
{
@@ -302,8 +277,9 @@ void TextField::keyPressed(gcn::KeyEvent &keyEvent)
return;
break;
- case 22: // Control code 22, SYNCHRONOUS IDLE, sent on Ctrl+v
- handlePaste();
+ case SDLK_v:
+ if (keyEvent.isControlPressed())
+ handlePaste();
break;
}
@@ -311,6 +287,12 @@ void TextField::keyPressed(gcn::KeyEvent &keyEvent)
fixScroll();
}
+void TextField::textInput(const TextInput &textInput)
+{
+ mText.insert(mCaretPosition, textInput.getText());
+ mCaretPosition += textInput.getText().length();
+}
+
void TextField::autoComplete()
{
if (mAutoComplete && mText.size() > 0)
@@ -383,7 +365,7 @@ void TextField::handlePaste()
std::string text = getText();
std::string::size_type caretPos = getCaretPosition();
- if (RetrieveBuffer(text, caretPos)) {
+ if (insertFromClipboard(text, caretPos)) {
setText(text);
setCaretPosition(caretPos);
}
diff --git a/src/gui/widgets/textfield.h b/src/gui/widgets/textfield.h
index 94cada41..bf60cbc3 100644
--- a/src/gui/widgets/textfield.h
+++ b/src/gui/widgets/textfield.h
@@ -26,6 +26,7 @@
#include <vector>
+class TextInput;
class ImageRect;
class TextField;
@@ -116,6 +117,11 @@ class TextField : public gcn::TextField
void keyPressed(gcn::KeyEvent &keyEvent);
/**
+ * Handle text input (should possibly be new event in Guichan).
+ */
+ void textInput(const TextInput &textInput);
+
+ /**
* Set the minimum value for a range
*/
void setMinimum(int min) { mMinimum = min; }
diff --git a/src/gui/windowmenu.cpp b/src/gui/windowmenu.cpp
index a06415fb..ff75e5d1 100644
--- a/src/gui/windowmenu.cpp
+++ b/src/gui/windowmenu.cpp
@@ -167,7 +167,7 @@ static std::string createShortcutCaption(const std::string& text,
if (key != KeyboardConfig::KEY_NO_VALUE)
{
caption += " (";
- caption += SDL_GetKeyName((SDLKey) keyboard.getKeyValue(key));
+ caption += SDL_GetKeyName((SDL_Scancode) keyboard.getKeyValue(key));
caption += ")";
}
return caption;
diff --git a/src/guild.cpp b/src/guild.cpp
index 2beee4f5..714ca010 100644
--- a/src/guild.cpp
+++ b/src/guild.cpp
@@ -169,7 +169,7 @@ void Guild::setRights(short rights)
bool Guild::isMember(GuildMember *member) const
{
- if (member->mGuild > 0 && member->mGuild != this)
+ if (member->mGuild != nullptr && member->mGuild != this)
return false;
MemberList::const_iterator itr = mMembers.begin(),
diff --git a/src/joystick.cpp b/src/joystick.cpp
index cc6e532b..a1da181c 100644
--- a/src/joystick.cpp
+++ b/src/joystick.cpp
@@ -37,7 +37,7 @@ void Joystick::init()
joystickCount = SDL_NumJoysticks();
logger->log("%i joysticks/gamepads found", joystickCount);
for (int i = 0; i < joystickCount; i++)
- logger->log("- %s", SDL_JoystickName(i));
+ logger->log("- %s", SDL_JoystickNameForIndex(i));
}
Joystick::Joystick(int no):
diff --git a/src/keyboardconfig.cpp b/src/keyboardconfig.cpp
index 0f4a46bf..39c99bc3 100644
--- a/src/keyboardconfig.cpp
+++ b/src/keyboardconfig.cpp
@@ -99,8 +99,8 @@ static KeyData const keyData[KeyboardConfig::KEY_TOTAL] = {
{"keyChatNextTab", SDLK_RIGHTBRACKET, _("Next Chat Tab")},
{"keyOK", SDLK_SPACE, _("Select OK")},
{"keyQuit", SDLK_ESCAPE, _("Quit")},
- {"keyIgnoreInput1", SDLK_LSUPER, _("Ignore input 1")},
- {"keyIgnoreInput2", SDLK_RSUPER, _("Ignore input 2")}
+ {"keyIgnoreInput1", SDLK_LGUI, _("Ignore input 1")},
+ {"keyIgnoreInput2", SDLK_RGUI, _("Ignore input 2")}
};
void KeyboardConfig::init()
@@ -231,5 +231,5 @@ bool KeyboardConfig::isKeyActive(int index) const
void KeyboardConfig::refreshActiveKeys()
{
- mActiveKeys = SDL_GetKeyState(NULL);
+ mActiveKeys = SDL_GetKeyboardState(NULL);
}
diff --git a/src/keyboardconfig.h b/src/keyboardconfig.h
index 8c744123..cb58dd90 100644
--- a/src/keyboardconfig.h
+++ b/src/keyboardconfig.h
@@ -227,7 +227,7 @@ class KeyboardConfig
KeyFunction mKey[KEY_TOTAL]; /**< Pointer to all the key data */
- uint8_t *mActiveKeys; /**< Stores a list of all the keys */
+ const uint8_t *mActiveKeys; /**< Stores a list of all the keys */
std::string mBindError;
};
diff --git a/src/net/download.cpp b/src/net/download.cpp
index bccba7a3..61cdf114 100644
--- a/src/net/download.cpp
+++ b/src/net/download.cpp
@@ -124,7 +124,7 @@ bool Download::start()
{
logger->log("Starting download: %s", mUrl.c_str());
- mThread = SDL_CreateThread(downloadThread, this);
+ mThread = SDL_CreateThread(downloadThread, "Download", this);
if (!mThread)
{
diff --git a/src/net/manaserv/messagehandler.h b/src/net/manaserv/messagehandler.h
index 6e0221cb..8949d34e 100644
--- a/src/net/manaserv/messagehandler.h
+++ b/src/net/manaserv/messagehandler.h
@@ -41,7 +41,7 @@ class MessageHandler : public Net::MessageHandler
virtual void handleMessage(MessageIn &msg) = 0;
};
-typedef const std::auto_ptr<MessageHandler> MessageHandlerPtr;
+typedef const std::unique_ptr<MessageHandler> MessageHandlerPtr;
} // namespace ManaServ
diff --git a/src/net/manaserv/messagein.h b/src/net/manaserv/messagein.h
index 89ae5ed8..1edc4fe7 100644
--- a/src/net/manaserv/messagein.h
+++ b/src/net/manaserv/messagein.h
@@ -52,7 +52,10 @@ class MessageIn
/**
* Returns the length of unread data.
*/
- unsigned int getUnreadLength() const { return mLength - mPos; }
+ unsigned int getUnreadLength() const
+ {
+ return (mPos < mLength) ? mLength - mPos : 0;
+ }
/**
* Reads an unsigned 8-bit integer from the message.
diff --git a/src/net/tmwa/loginhandler.cpp b/src/net/tmwa/loginhandler.cpp
index 51c757cc..77b545fd 100644
--- a/src/net/tmwa/loginhandler.cpp
+++ b/src/net/tmwa/loginhandler.cpp
@@ -298,7 +298,7 @@ void LoginHandler::sendLoginRegister(const std::string &username,
const std::string &password)
{
MessageOut outMsg(0x0064);
- outMsg.writeInt32(0); // client version
+ outMsg.writeInt32(20); // client version
outMsg.writeString(username, 24);
outMsg.writeString(password, 24);
diff --git a/src/net/tmwa/messagehandler.h b/src/net/tmwa/messagehandler.h
index 2b1f5b7e..b598f896 100644
--- a/src/net/tmwa/messagehandler.h
+++ b/src/net/tmwa/messagehandler.h
@@ -49,7 +49,7 @@ class MessageHandler : public Net::MessageHandler
Network *mNetwork;
};
-typedef const std::auto_ptr<MessageHandler> MessageHandlerPtr;
+typedef const std::unique_ptr<MessageHandler> MessageHandlerPtr;
}
diff --git a/src/net/tmwa/messagein.h b/src/net/tmwa/messagein.h
index 48121187..2f66ca28 100644
--- a/src/net/tmwa/messagein.h
+++ b/src/net/tmwa/messagein.h
@@ -50,7 +50,10 @@ class MessageIn
/**
* Returns the length of unread data.
*/
- unsigned int getUnreadLength() const { return mLength - mPos; }
+ unsigned int getUnreadLength() const
+ {
+ return (mPos < mLength) ? mLength - mPos : 0;
+ }
/**
* Reads an unsigned 8-bit integer from the message.
diff --git a/src/net/tmwa/network.cpp b/src/net/tmwa/network.cpp
index 3a02deba..ed564b46 100644
--- a/src/net/tmwa/network.cpp
+++ b/src/net/tmwa/network.cpp
@@ -77,7 +77,7 @@ uint16_t packet_lengths[0x220] = {
11, 7,VAR, 67, 12, 18,114, 6, 3, 6, 26, 26, 26, 26, 2, 3,
// #0x01C0
2, 14, 10,VAR, 22, 22, 4, 2, 13, 97, 0, 9, 9, 29, 6, 28,
- 8, 14, 10, 35, 6, 8, 4, 11, 54, 53, 60, 2,VAR, 47, 33, 6,
+ 8, 14, 10, 35, 6,VAR, 4, 11, 54, 53, 60, 2,VAR, 47, 33, 6,
30, 8, 34, 14, 2, 6, 26, 2, 28, 81, 6, 10, 26, 2,VAR,VAR,
VAR,VAR, 20, 10, 32, 9, 34, 14, 2, 6, 48, 56,VAR, 4, 5, 10,
// #0x0200
@@ -159,7 +159,7 @@ bool Network::connect(ServerInfo server)
mToSkip = 0;
mState = CONNECTING;
- mWorkerThread = SDL_CreateThread(networkThread, this);
+ mWorkerThread = SDL_CreateThread(networkThread, "Network", this);
if (!mWorkerThread)
{
setError("Unable to create network worker thread");
diff --git a/src/net/tmwa/tradehandler.cpp b/src/net/tmwa/tradehandler.cpp
index 40e37594..a02056a4 100644
--- a/src/net/tmwa/tradehandler.cpp
+++ b/src/net/tmwa/tradehandler.cpp
@@ -207,6 +207,11 @@ void TradeHandler::handleMessage(MessageIn &msg)
SERVER_NOTICE(_("Failed adding item. Trade "
"partner has no free slot."))
break;
+ case 3:
+ // Add item failed - non tradable item
+ SERVER_NOTICE(_("Failed adding item. You "
+ "cant trade this item."))
+ break;
default:
SERVER_NOTICE(_("Failed adding item for "
"unknown reason."))
diff --git a/src/openglgraphics.cpp b/src/openglgraphics.cpp
index 28fd47f6..0b79e933 100644
--- a/src/openglgraphics.cpp
+++ b/src/openglgraphics.cpp
@@ -63,7 +63,13 @@ OpenGLGraphics::~OpenGLGraphics()
void OpenGLGraphics::setSync(bool sync)
{
+ if (mSync == sync)
+ return;
+
mSync = sync;
+
+ if (mContext)
+ SDL_GL_SetSwapInterval(sync ? 1 : 0);
}
void OpenGLGraphics::setReduceInputLag(bool reduceInputLag)
@@ -71,55 +77,59 @@ void OpenGLGraphics::setReduceInputLag(bool reduceInputLag)
mReduceInputLag = reduceInputLag;
}
-bool OpenGLGraphics::setVideoMode(int w, int h, int bpp, bool fs, bool hwaccel)
+bool OpenGLGraphics::setVideoMode(int w, int h, bool fs)
{
logger->log("Setting video mode %dx%d %s",
w, h, fs ? "fullscreen" : "windowed");
- int displayFlags = SDL_ANYFORMAT | SDL_OPENGL;
+ // TODO_SDL2: Support SDL_WINDOW_ALLOW_HIGHDPI, but check handling of clip area
- const double targetRatio = (double) 640 / 360; // 1.77778
- const double requestedRatio = (double) w / h;
+ int windowFlags = SDL_WINDOW_OPENGL;
- if (requestedRatio < targetRatio) {
- // Screen is higher / narrower than target aspect ratio: calculate
- // scale based on height.
- mScale = (int) std::floor((double) h / 360);
- } else {
- mScale = (int) std::floor((double) w / 640);
- }
-
- mWidth = w / mScale;
- mHeight = h / mScale;
- mBpp = bpp;
- mFullscreen = fs;
- mHWAccel = hwaccel;
+ mScale = getScale(w, h);
if (fs)
{
- displayFlags |= SDL_FULLSCREEN;
+ windowFlags |= SDL_WINDOW_FULLSCREEN;
}
else
{
// Resizing currently not supported on Windows, where it would require
// reuploading all textures.
#if !defined(_WIN32)
- displayFlags |= SDL_RESIZABLE;
+ windowFlags |= SDL_WINDOW_RESIZABLE;
#endif
}
SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, 1);
- if (!(mTarget = SDL_SetVideoMode(w, h, bpp, displayFlags)))
+ SDL_Window *window = SDL_CreateWindow("Mana",
+ SDL_WINDOWPOS_UNDEFINED,
+ SDL_WINDOWPOS_UNDEFINED,
+ w, h, windowFlags);
+ if (!window) {
+ logger->log("Failed to create window: %s", SDL_GetError());
return false;
+ }
+
+ SDL_SetWindowMinimumSize(window, 640, 360);
+
+ SDL_GLContext glContext = SDL_GL_CreateContext(window);
+ if (!glContext) {
+ logger->log("Failed to create OpenGL context: %s", SDL_GetError());
+ return false;
+ }
+
+ mTarget = window;
+ mContext = glContext;
+ mWidth = w / mScale;
+ mHeight = h / mScale;
+ mFullscreen = fs;
-#ifdef __APPLE__
if (mSync)
{
- const GLint VBL = 1;
- CGLSetParameter(CGLGetCurrentContext(), kCGLCPSwapInterval, &VBL);
+ SDL_GL_SetSwapInterval(1);
}
-#endif
// Setup OpenGL
glViewport(0, 0, mWidth * mScale, mHeight * mScale);
@@ -152,6 +162,19 @@ bool OpenGLGraphics::setVideoMode(int w, int h, int bpp, bool fs, bool hwaccel)
return true;
}
+void OpenGLGraphics::videoResized(int w, int h)
+{
+ _endDraw();
+
+ mScale = getScale(w, h);
+ mWidth = w / mScale;
+ mHeight = h / mScale;
+
+ glViewport(0, 0, w, h);
+
+ _beginDraw();
+}
+
static inline void drawQuad(Image *image,
int srcX, int srcY, int dstX, int dstY,
int width, int height)
@@ -623,7 +646,7 @@ void OpenGLGraphics::drawRescaledImagePattern(Image *image,
void OpenGLGraphics::updateScreen()
{
- SDL_GL_SwapBuffers();
+ SDL_GL_SwapWindow(mTarget);
/*
* glFinish flushes all OpenGL commands and makes sure they have been
@@ -647,7 +670,7 @@ void OpenGLGraphics::_beginDraw()
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
- glOrtho(0.0, (double) mWidth, (double) mHeight, 0.0, -1.0, 1.0);
+ glOrtho(0.0, (double)mWidth, (double)mHeight, 0.0, -1.0, 1.0);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
@@ -669,8 +692,8 @@ void OpenGLGraphics::_endDraw()
SDL_Surface* OpenGLGraphics::getScreenshot()
{
- int h = mTarget->h;
- int w = mTarget->w;
+ int w, h;
+ SDL_GL_GetDrawableSize(mTarget, &w, &h);
GLint pack = 1;
SDL_Surface *screenshot = SDL_CreateRGBSurface(
@@ -721,13 +744,14 @@ bool OpenGLGraphics::pushClipArea(gcn::Rectangle area)
transY = -mClipStack.top().yOffset;
}
+ // Skip Graphics::popClipArea since we don't need to interact with SDL2
bool result = gcn::Graphics::pushClipArea(area);
transX += mClipStack.top().xOffset;
transY += mClipStack.top().yOffset;
int x = (int) (mClipStack.top().x * mScale);
- int y = mTarget->h - (int) ((mClipStack.top().y +
+ int y = (int) ((mHeight - mClipStack.top().y -
mClipStack.top().height) * mScale);
int width = (int) (mClipStack.top().width * mScale);
int height = (int) (mClipStack.top().height * mScale);
@@ -741,13 +765,14 @@ bool OpenGLGraphics::pushClipArea(gcn::Rectangle area)
void OpenGLGraphics::popClipArea()
{
+ // Skip Graphics::popClipArea since we don't need to interact with SDL2
gcn::Graphics::popClipArea();
if (mClipStack.empty())
return;
int x = (int) (mClipStack.top().x * mScale);
- int y = mTarget->h - (int) ((mClipStack.top().y +
+ int y = (int) ((mHeight - mClipStack.top().y -
mClipStack.top().height) * mScale);
int width = (int) (mClipStack.top().width * mScale);
int height = (int) (mClipStack.top().height * mScale);
diff --git a/src/openglgraphics.h b/src/openglgraphics.h
index 63c32261..01bca360 100644
--- a/src/openglgraphics.h
+++ b/src/openglgraphics.h
@@ -37,8 +37,8 @@ class OpenGLGraphics : public Graphics
~OpenGLGraphics();
/**
- * Sets whether vertical refresh syncing is enabled. Takes effect after
- * the next call to setVideoMode(). Only implemented on MacOS for now.
+ * Sets whether vertical refresh syncing is enabled. Takes effect
+ * immediately.
*/
void setSync(bool sync);
bool getSync() const { return mSync; }
@@ -53,7 +53,9 @@ class OpenGLGraphics : public Graphics
void setReduceInputLag(bool reduceInputLag);
bool getReduceInputLag() const { return mReduceInputLag; }
- bool setVideoMode(int w, int h, int bpp, bool fs, bool hwaccel);
+ bool setVideoMode(int w, int h, bool fs);
+
+ void videoResized(int w, int h);
bool drawImage(Image *image,
int srcX, int srcY,
@@ -118,6 +120,7 @@ class OpenGLGraphics : public Graphics
void drawQuadArrayii(int size);
+ SDL_GLContext mContext = nullptr;
GLfloat *mFloatTexArray;
GLint *mIntTexArray;
GLint *mIntVertArray;
diff --git a/src/party.cpp b/src/party.cpp
index 344bbdad..126a63c1 100644
--- a/src/party.cpp
+++ b/src/party.cpp
@@ -168,7 +168,7 @@ void Party::setRights(short rights)
bool Party::isMember(PartyMember *member) const
{
- if (member->mParty > 0 && member->mParty != this)
+ if (member->mParty != nullptr && member->mParty != this)
return false;
MemberList::const_iterator itr = mMembers.begin(),
diff --git a/src/resources/ambientlayer.cpp b/src/resources/ambientlayer.cpp
index c31afbac..301927f8 100644
--- a/src/resources/ambientlayer.cpp
+++ b/src/resources/ambientlayer.cpp
@@ -33,25 +33,6 @@ AmbientLayer::AmbientLayer(Image *img, float parallax,
mKeepRatio(keepRatio)
{
mImage->incRef();
-
- if (keepRatio && !mImage->useOpenGL()
- && defaultScreenWidth != 0
- && defaultScreenHeight != 0
- && graphics->getWidth() != defaultScreenWidth
- && graphics->getHeight() != defaultScreenHeight)
- {
- // Rescale the overlay to keep the ratio as if we were on
- // the default resolution...
- Image *rescaledOverlay = mImage->SDLgetScaledImage(
- (int) mImage->getWidth() / defaultScreenWidth * graphics->getWidth(),
- (int) mImage->getHeight() / defaultScreenHeight * graphics->getHeight());
-
- if (rescaledOverlay)
- {
- mImage->decRef();
- mImage = rescaledOverlay;
- }
- }
}
AmbientLayer::~AmbientLayer()
@@ -86,7 +67,7 @@ void AmbientLayer::update(int timePassed, float dx, float dy)
void AmbientLayer::draw(Graphics *graphics, int x, int y)
{
- if (!mImage->useOpenGL() || !mKeepRatio)
+ if (!mKeepRatio)
graphics->drawImagePattern(mImage,
(int) -mPosX, (int) -mPosY, x + (int) mPosX, y + (int) mPosY);
else
@@ -94,5 +75,4 @@ void AmbientLayer::draw(Graphics *graphics, int x, int y)
(int) -mPosX, (int) -mPosY, x + (int) mPosX, y + (int) mPosY,
(int) mImage->getWidth() / defaultScreenWidth * graphics->getWidth(),
(int) mImage->getHeight() / defaultScreenHeight * graphics->getHeight());
-
}
diff --git a/src/resources/image.cpp b/src/resources/image.cpp
index 7e592198..6f2609b0 100644
--- a/src/resources/image.cpp
+++ b/src/resources/image.cpp
@@ -29,10 +29,8 @@
#endif
#include "log.h"
-#include "configuration.h"
#include <SDL_image.h>
-#include <SDL_rotozoom.h>
#ifdef USE_OPENGL
bool Image::mUseOpenGL = false;
@@ -40,47 +38,38 @@ bool Image::mPowerOfTwoTextures = true;
int Image::mTextureType = 0;
int Image::mTextureSize = 0;
#endif
-bool Image::mEnableAlphaCache = false;
// The low CPU mode is disabled per default
bool Image::mDisableTransparency = false;
-Image::Image(SDL_Surface *image, bool hasAlphaChannel, Uint8 *alphaChannel):
+SDL_Renderer *Image::mRenderer;
+
+Image::Image(SDL_Texture *texture, int width, int height):
mAlpha(1.0f),
- mSDLSurface(image),
- mAlphaChannel(alphaChannel),
- mHasAlphaChannel(hasAlphaChannel)
+ mTexture(texture)
{
#ifdef USE_OPENGL
mGLImage = 0;
#endif
- mUseAlphaCache = Image::mEnableAlphaCache;
-
mBounds.x = 0;
mBounds.y = 0;
+ mBounds.w = width;
+ mBounds.h = height;
- mLoaded = false;
+ mLoaded = mTexture != nullptr;
- if (mSDLSurface)
+ if (!mLoaded)
{
- mBounds.w = mSDLSurface->w;
- mBounds.h = mSDLSurface->h;
-
- mLoaded = true;
- }
- else
logger->log(
"Image::Image(SDL_Surface*): Couldn't load invalid Surface!");
+ }
}
#ifdef USE_OPENGL
Image::Image(GLuint glimage, int width, int height, int texWidth, int texHeight):
mAlpha(1.0f),
- mSDLSurface(0),
- mAlphaChannel(0),
- mHasAlphaChannel(true),
- mUseAlphaCache(false),
+ mTexture(0),
mGLImage(glimage),
mTexWidth(texWidth),
mTexHeight(texHeight)
@@ -140,10 +129,8 @@ Resource *Image::load(SDL_RWops *rw, Dye const &dye)
rgba.Gmask = 0x00FF0000; rgba.Gloss = 0; rgba.Gshift = 16;
rgba.Bmask = 0x0000FF00; rgba.Bloss = 0; rgba.Bshift = 8;
rgba.Amask = 0x000000FF; rgba.Aloss = 0; rgba.Ashift = 0;
- rgba.colorkey = 0;
- rgba.alpha = 255;
- SDL_Surface *surf = SDL_ConvertSurface(tmpImage, &rgba, SDL_SWSURFACE);
+ SDL_Surface *surf = SDL_ConvertSurface(tmpImage, &rgba, 0);
SDL_FreeSurface(tmpImage);
Uint32 *pixels = static_cast< Uint32 * >(surf->pixels);
@@ -173,34 +160,14 @@ Image *Image::load(SDL_Surface *tmpImage)
return _SDLload(tmpImage);
}
-void Image::SDLcleanCache()
-{
- ResourceManager *resman = ResourceManager::getInstance();
-
- for (std::map<float, SDL_Surface*>::iterator
- i = mAlphaCache.begin(), i_end = mAlphaCache.end();
- i != i_end; ++i)
- {
- if (mSDLSurface != i->second)
- resman->scheduleDelete(i->second);
- i->second = 0;
- }
- mAlphaCache.clear();
-}
-
void Image::unload()
{
mLoaded = false;
- if (mSDLSurface)
+ if (mTexture)
{
- SDLcleanCache();
- // Free the image surface.
- SDL_FreeSurface(mSDLSurface);
- mSDLSurface = NULL;
-
- delete[] mAlphaChannel;
- mAlphaChannel = NULL;
+ SDL_DestroyTexture(mTexture);
+ mTexture = NULL;
}
#ifdef USE_OPENGL
@@ -221,27 +188,6 @@ bool Image::useOpenGL()
#endif
}
-bool Image::hasAlphaChannel()
-{
- if (!mLoaded)
- return false;
-
-#ifdef USE_OPENGL
- if (mUseOpenGL)
- return true;
-#endif
-
- return mHasAlphaChannel;
-}
-
-SDL_Surface *Image::getByAlpha(float alpha)
-{
- std::map<float, SDL_Surface*>::iterator it = mAlphaCache.find(alpha);
- if (it != mAlphaCache.end())
- return (*it).second;
- return 0;
-}
-
void Image::setAlpha(float alpha)
{
if (!useOpenGL() && mDisableTransparency)
@@ -253,188 +199,26 @@ void Image::setAlpha(float alpha)
if (alpha < 0.0f || alpha > 1.0f)
return;
- if (mSDLSurface)
- {
- if (mUseAlphaCache)
- {
- SDL_Surface *surface = getByAlpha(mAlpha);
- if (!surface)
- {
- if (mAlphaCache.size() > 100)
- SDLcleanCache();
-
- mAlphaCache[mAlpha] = mSDLSurface;
- }
- surface = getByAlpha(alpha);
- if (surface)
- {
- mAlphaCache.erase(alpha);
- mSDLSurface = surface;
- mAlpha = alpha;
- return;
- }
- else
- {
- mSDLSurface = Image::SDLduplicateSurface(mSDLSurface);
- }
- }
-
- mAlpha = alpha;
-
- if (!hasAlphaChannel())
- {
- // Set the alpha value this image is drawn at
- SDL_SetAlpha(mSDLSurface, SDL_SRCALPHA, (int) (255 * mAlpha));
- }
- else
- {
- if (SDL_MUSTLOCK(mSDLSurface))
- SDL_LockSurface(mSDLSurface);
-
- // Precompute as much as possible
- int maxHeight = std::min((mBounds.y + mBounds.h), mSDLSurface->h);
- int maxWidth = std::min((mBounds.x + mBounds.w), mSDLSurface->w);
- int i = 0;
-
- for (int y = mBounds.y; y < maxHeight; y++)
- for (int x = mBounds.x; x < maxWidth; x++)
- {
- i = y * mSDLSurface->w + x;
- // Only change the pixel if it was visible at load time...
- Uint8 sourceAlpha = mAlphaChannel[i];
- if (sourceAlpha > 0)
- {
- Uint8 r, g, b, a;
- SDL_GetRGBA(((Uint32*) mSDLSurface->pixels)[i],
- mSDLSurface->format,
- &r, &g, &b, &a);
-
- a = (Uint8) (sourceAlpha * mAlpha);
-
- // Here is the pixel we want to set
- ((Uint32 *)(mSDLSurface->pixels))[i] =
- SDL_MapRGBA(mSDLSurface->format, r, g, b, a);
- }
- }
-
- if (SDL_MUSTLOCK(mSDLSurface))
- SDL_UnlockSurface(mSDLSurface);
- }
- }
- else
- {
- mAlpha = alpha;
- }
-}
-
-Image *Image::SDLgetScaledImage(int width, int height)
-{
- if (width == 0 || height == 0)
- return 0;
+ mAlpha = alpha;
- // Increase our reference count and return ourselves in case of same size
- if (width == getWidth() && height == getHeight())
+ if (mTexture)
{
- incRef();
- return this;
- }
-
- if (!mSDLSurface)
- return 0;
-
- ResourceManager *resman = ResourceManager::getInstance();
-
- // Generate a unique ID path for storing the scaled version in the
- // resource manager.
- std::string idPath = getIdPath();
- idPath += ":scaled:";
- idPath += toString(width);
- idPath += "x";
- idPath += toString(height);
-
- // Try whether a scaled version is already available
- Image *scaledImage = static_cast<Image*>(resman->get(idPath));
-
- if (!scaledImage)
- {
- // No scaled version with this size exists already, so create one
- SDL_Surface *scaledSurface = zoomSurface(mSDLSurface,
- (double) width / getWidth(),
- (double) height / getHeight(),
- 1);
-
- if (scaledSurface)
- {
- scaledImage = load(scaledSurface);
- SDL_FreeSurface(scaledSurface);
-
- // Place the scaled image in the resource manager
- resman->addResource(idPath, scaledImage);
- }
+ SDL_SetTextureAlphaMod(mTexture, (Uint8) (255 * mAlpha));
}
-
- return scaledImage;
}
-SDL_Surface* Image::SDLduplicateSurface(SDL_Surface* tmpImage)
+Image *Image::_SDLload(SDL_Surface *image)
{
- if (!tmpImage || !tmpImage->format)
+ if (!image || !mRenderer)
return NULL;
- return SDL_ConvertSurface(tmpImage, tmpImage->format, SDL_SWSURFACE);
+ SDL_Texture *texture = SDL_CreateTextureFromSurface(mRenderer, image);
+ return new Image(texture, image->w, image->h);
}
-Image *Image::_SDLload(SDL_Surface *tmpImage)
+void Image::setRenderer(SDL_Renderer *renderer)
{
- if (!tmpImage)
- return NULL;
-
- bool hasAlpha = false;
-
- // The alpha channel to be filled with alpha values
- Uint8 *alphaChannel = new Uint8[tmpImage->w * tmpImage->h];
-
- if (tmpImage->format->BitsPerPixel == 32)
- {
- // Figure out whether the image uses its alpha layer
- for (int i = 0; i < tmpImage->w * tmpImage->h; ++i)
- {
- Uint8 r, g, b, a;
- SDL_GetRGBA(
- ((Uint32*) tmpImage->pixels)[i],
- tmpImage->format,
- &r, &g, &b, &a);
-
- if (a != 255)
- hasAlpha = true;
-
- alphaChannel[i] = a;
- }
- }
-
- SDL_Surface *image;
-
- // Convert the surface to the current display format
- if (hasAlpha)
- image = SDL_DisplayFormatAlpha(tmpImage);
- else
- {
- image = SDL_DisplayFormat(tmpImage);
-
- // We also delete the alpha channel since
- // it's not used.
- delete[] alphaChannel;
- alphaChannel = NULL;
- }
-
- if (!image)
- {
- logger->log("Error: Image convert failed.");
- delete[] alphaChannel;
- return NULL;
- }
-
- return new Image(image, hasAlpha, alphaChannel);
+ mRenderer = renderer;
}
#ifdef USE_OPENGL
@@ -489,7 +273,7 @@ Image *Image::_GLload(SDL_Surface *image)
}
// Make sure the alpha channel is not used, but copied to destination
- SDL_SetAlpha(oldImage, 0, SDL_ALPHA_OPAQUE);
+ SDL_SetSurfaceBlendMode(oldImage, SDL_BLENDMODE_NONE);
SDL_BlitSurface(oldImage, NULL, image, NULL);
}
@@ -583,38 +367,24 @@ Image *Image::getSubImage(int x, int y, int width, int height)
mTexWidth, mTexHeight);
#endif
- return new SubImage(this, mSDLSurface,
+ return new SubImage(this, mTexture,
mBounds.x + x,
mBounds.y + y,
width, height);
}
-void Image::SDLterminateAlphaCache()
-{
- SDLcleanCache();
- mUseAlphaCache = false;
-}
-
//============================================================================
// SubImage Class
//============================================================================
-SubImage::SubImage(Image *parent, SDL_Surface *image,
+SubImage::SubImage(Image *parent, SDL_Texture *texture,
int x, int y, int width, int height):
- Image(image),
+ Image(texture, width, height),
mParent(parent)
{
if (mParent)
{
mParent->incRef();
- mParent->SDLterminateAlphaCache();
- mHasAlphaChannel = mParent->hasAlphaChannel();
- mAlphaChannel = mParent->SDLgetAlphaChannel();
- }
- else
- {
- mHasAlphaChannel = false;
- mAlphaChannel = 0;
}
// Set up the rectangle.
@@ -622,7 +392,6 @@ SubImage::SubImage(Image *parent, SDL_Surface *image,
mBounds.y = y;
mBounds.w = width;
mBounds.h = height;
- mUseAlphaCache = false;
}
#ifdef USE_OPENGL
@@ -644,10 +413,8 @@ SubImage::SubImage(Image *parent, GLuint image,
SubImage::~SubImage()
{
- // Avoid destruction of the image
- mSDLSurface = 0;
- // Avoid possible destruction of its alpha channel
- mAlphaChannel = 0;
+ // Avoid destruction of the texture
+ mTexture = nullptr;
#ifdef USE_OPENGL
mGLImage = 0;
#endif
diff --git a/src/resources/image.h b/src/resources/image.h
index b762bf2a..efe2262e 100644
--- a/src/resources/image.h
+++ b/src/resources/image.h
@@ -37,8 +37,6 @@
#include <SDL_opengl.h>
#endif
-#include <map>
-
class Dye;
class Position;
@@ -129,12 +127,6 @@ class Image : public Resource
*/
Image *getSubImage(int x, int y, int width, int height);
- /**
- * Tells if the image has got an alpha channel
- * @return true if it's true, false otherwise.
- */
- bool hasAlphaChannel();
-
// SDL only public functions
/**
@@ -146,31 +138,7 @@ class Image : public Resource
static bool SDLisTransparencyDisabled()
{ return mDisableTransparency; }
- /**
- * Gets an scaled instance of an image. The returned image is managed
- * by the ResourceManager.
- *
- * @param width The desired width of the scaled image.
- * @param height The desired height of the scaled image.
- *
- * @return An Image resource, or 0 on failure.
- */
- Image *SDLgetScaledImage(int width, int height);
-
- /**
- * Get the alpha Channel of a SDL surface.
- */
- Uint8 *SDLgetAlphaChannel() const
- { return mAlphaChannel; }
-
- SDL_Surface* SDLduplicateSurface(SDL_Surface* tmpImage);
-
- void SDLcleanCache();
-
- void SDLterminateAlphaCache();
-
- static void SDLsetEnableAlphaCache(bool n)
- { mEnableAlphaCache = n; }
+ static void setRenderer(SDL_Renderer *renderer);
#ifdef USE_OPENGL
@@ -204,30 +172,18 @@ class Image : public Resource
// -----------------------
/** SDL Constructor */
- Image(SDL_Surface *image, bool hasAlphaChannel = false,
- Uint8 *alphaChannel = NULL);
+ Image(SDL_Texture *texture, int width, int height);
- /** SDL_Surface to SDL_Surface Image loader */
+ /** SDL_Surface to SDL_Texture Image loader */
static Image *_SDLload(SDL_Surface *tmpImage);
- SDL_Surface *getByAlpha(float alpha);
-
- SDL_Surface *mSDLSurface;
-
- /** Alpha Channel pointer used for 32bit based SDL surfaces */
- Uint8 *mAlphaChannel;
- bool mHasAlphaChannel;
-
- /** Alpha cache: The cache stores a copy of the image
- for specific requested opacities, hence, increasing
- the image disply speed */
- std::map<float, SDL_Surface*> mAlphaCache;
- bool mUseAlphaCache;
- static bool mEnableAlphaCache;
+ SDL_Texture *mTexture;
/** Stores whether the transparency is disabled */
static bool mDisableTransparency;
+ static SDL_Renderer *mRenderer;
+
// -----------------------
// OpenGL protected members
// -----------------------
@@ -261,7 +217,7 @@ class Image : public Resource
class SubImage : public Image
{
public:
- SubImage(Image *parent, SDL_Surface *image,
+ SubImage(Image *parent, SDL_Texture *texture,
int x, int y, int width, int height);
#ifdef USE_OPENGL
SubImage(Image *parent, GLuint image, int x, int y,
diff --git a/src/resources/settingsmanager.cpp b/src/resources/settingsmanager.cpp
index 940ebb59..a26fae9d 100644
--- a/src/resources/settingsmanager.cpp
+++ b/src/resources/settingsmanager.cpp
@@ -85,7 +85,8 @@ namespace SettingsManager
NPCDB::unload();
SpecialDB::unload();
MonsterDB::unload();
- itemDb->unload();
+ if (itemDb)
+ itemDb->unload();
hairDB.unload();
Attributes::unload();
}
@@ -209,4 +210,3 @@ namespace SettingsManager
}
}
-
diff --git a/src/resources/theme.cpp b/src/resources/theme.cpp
index 8db05be9..84d6311b 100644
--- a/src/resources/theme.cpp
+++ b/src/resources/theme.cpp
@@ -88,8 +88,8 @@ void Skin::updateAlpha(float minimumOpacityAllowed)
void Skin::setAlpha(float alpha)
{
- for_each(mBorder.grid, mBorder.grid + 9,
- std::bind2nd(std::mem_fun(&Image::setAlpha), alpha));
+ std::for_each(mBorder.grid, mBorder.grid + 9,
+ [=] (Image *img) { img->setAlpha(alpha); });
mCloseImage->setAlpha(alpha);
mStickyImageUp->setAlpha(alpha);
diff --git a/src/sound.cpp b/src/sound.cpp
index 1af1f136..44f55cba 100644
--- a/src/sound.cpp
+++ b/src/sound.cpp
@@ -22,7 +22,6 @@
#include <SDL.h>
#include "configuration.h"
-#include "game.h"
#include "localplayer.h"
#include "log.h"
#include "sound.h"
@@ -112,7 +111,6 @@ void Sound::info()
{
SDL_version compiledVersion;
const SDL_version *linkedVersion;
- char driver[40] = "Unknown";
const char *format = "Unknown";
int rate = 0;
Uint16 audioFormat = 0;
@@ -121,7 +119,7 @@ void Sound::info()
MIX_VERSION(&compiledVersion);
linkedVersion = Mix_Linked_Version();
- SDL_AudioDriverName(driver, 40);
+ const char *driver = SDL_GetCurrentAudioDriver();
Mix_QuerySpec(&rate, &audioFormat, &channels);
switch (audioFormat)
diff --git a/src/utils/copynpaste.cpp b/src/utils/copynpaste.cpp
index 2bb8fb49..ccb36d79 100644
--- a/src/utils/copynpaste.cpp
+++ b/src/utils/copynpaste.cpp
@@ -1,7 +1,6 @@
/*
- * Retrieve string pasted depending on OS mechanisms.
- * Copyright (C) 2001-2010 Wormux Team
- * Copyright (C) 2010-2012 The Mana Developers
+ * Clipboard Interaction.
+ * Copyright (C) 2010-2024 The Mana Developers
*
* This file is part of The Mana Client.
*
@@ -19,301 +18,18 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-/*
- * IMPORTANT!
- *
- * This code was taken from Wormux svn trunk at Feb 25 2010. Please don't
- * make any unnecessary modifications, and try to sync up modifications
- * when possible.
- */
-
-#ifdef _MSC_VER
-# include "msvc/config.h"
-#elif defined(HAVE_CONFIG_H)
-# include "config.h"
-#endif
-
-#include <SDL_syswm.h>
-#include "copynpaste.h"
-
-#ifdef _WIN32
-bool RetrieveBuffer(std::string& text, std::string::size_type& pos)
-{
- bool ret = false;
-
- if (!OpenClipboard(NULL))
- return false;
-
- HANDLE h = GetClipboardData(CF_UNICODETEXT);
- if (h)
- {
- LPCWSTR data = (LPCWSTR)GlobalLock(h);
+#include "utils/copynpaste.h"
- if (data)
- {
- int len = WideCharToMultiByte(CP_UTF8, 0, data, -1, NULL, 0, NULL, NULL);
- if (len > 0)
- {
- // Convert from UTF-16 to UTF-8
- void *temp = malloc(len);
- if (WideCharToMultiByte(CP_UTF8, 0, data, -1, (LPSTR)temp, len, NULL, NULL))
- {
- text.insert(pos, (char*)temp);
- pos += len-1;
- }
- free(temp);
- ret = true;
- }
- }
- GlobalUnlock(h);
- }
- else
- {
- h = GetClipboardData(CF_TEXT);
-
- if (h)
- {
- const char *data = (char*)GlobalLock(h);
- if (data)
- {
- text.insert(pos, data);
- pos += strlen(data);
- ret = true;
- }
- GlobalUnlock(h);
- }
- }
-
- CloseClipboard();
- return ret;
-}
-#elif defined(__APPLE__)
+#include <SDL.h>
-#ifdef Status
-#undef Status
-#endif
-
-#include <Carbon/Carbon.h>
-
-// Sorry for the very long code, all nicer OS X APIs are coded in Objective C and not C!
-// Also it does very thorough error handling
-bool GetDataFromPasteboard( PasteboardRef inPasteboard, char* flavorText /* out */, const int bufSize )
+bool insertFromClipboard(std::string &text, std::string::size_type &pos)
{
- OSStatus err = noErr;
- PasteboardSyncFlags syncFlags;
- ItemCount itemCount;
-
- syncFlags = PasteboardSynchronize( inPasteboard );
-
- //require_action( syncFlags & kPasteboardModified, PasteboardOutOfSync,
- // err = badPasteboardSyncErr );
-
- err = PasteboardGetItemCount( inPasteboard, &itemCount );
- require_noerr( err, CantGetPasteboardItemCount );
-
- for (UInt32 itemIndex = 1; itemIndex <= itemCount; itemIndex++)
- {
- PasteboardItemID itemID;
- CFArrayRef flavorTypeArray;
- CFIndex flavorCount;
-
- err = PasteboardGetItemIdentifier( inPasteboard, itemIndex, &itemID );
- require_noerr( err, CantGetPasteboardItemIdentifier );
-
- err = PasteboardCopyItemFlavors( inPasteboard, itemID, &flavorTypeArray );
- require_noerr( err, CantCopyPasteboardItemFlavors );
-
- flavorCount = CFArrayGetCount( flavorTypeArray );
-
- for (CFIndex flavorIndex = 0; flavorIndex < flavorCount; flavorIndex++)
- {
- CFStringRef flavorType;
- CFDataRef flavorData;
- CFIndex flavorDataSize;
- flavorType = (CFStringRef)CFArrayGetValueAtIndex(flavorTypeArray, flavorIndex);
-
- // we're only interested by text...
- if (UTTypeConformsTo(flavorType, CFSTR("public.utf8-plain-text")))
- {
- err = PasteboardCopyItemFlavorData( inPasteboard, itemID,
- flavorType, &flavorData );
- require_noerr( err, CantCopyFlavorData );
- flavorDataSize = CFDataGetLength( flavorData );
- flavorDataSize = (flavorDataSize<254) ? flavorDataSize : 254;
-
- if (flavorDataSize+2 > bufSize)
- {
- fprintf(stderr, "Cannot copy clipboard, contents is too big!\n");
- return false;
- }
-
- for (short dataIndex = 0; dataIndex <= flavorDataSize; dataIndex++)
- {
- char byte = *(CFDataGetBytePtr( flavorData ) + dataIndex);
- flavorText[dataIndex] = byte;
- }
-
- flavorText[flavorDataSize] = '\0';
- flavorText[flavorDataSize+1] = '\n';
-
- CFRelease (flavorData);
- return true;
- }
-
- continue;
- CantCopyFlavorData: fprintf(stderr, "Cannot copy clipboard, CantCopyFlavorData!\n");
- }
-
- CFRelease (flavorTypeArray);
- continue;
-
- CantCopyPasteboardItemFlavors: fprintf(stderr, "Cannot copy clipboard, CantCopyPasteboardItemFlavors!\n"); continue;
- CantGetPasteboardItemIdentifier: fprintf(stderr, "Cannot copy clipboard, CantGetPasteboardItemIdentifier!\n"); continue;
- }
- fprintf(stderr, "Cannot copy clipboard, found no acceptable flavour!\n");
- return false;
-
- CantGetPasteboardItemCount: fprintf(stderr, "Cannot copy clipboard, CantGetPasteboardItemCount!\n"); return false;
- //PasteboardOutOfSync: fprintf(stderr, "Cannot copy clipboard, PasteboardOutOfSync!\n"); return false;
-}
-
-bool getClipBoard(char* text /* out */, const int bufSize )
-{
- OSStatus err = noErr;
-
- PasteboardRef theClipboard;
- err = PasteboardCreate( kPasteboardClipboard, &theClipboard );
- require_noerr( err, PasteboardCreateFailed );
-
- if (!GetDataFromPasteboard(theClipboard, text, bufSize))
- {
- fprintf(stderr, "Cannot copy clipboard, GetDataFromPasteboardFailed!\n");
- return false;
- }
-
- CFRelease(theClipboard);
-
- return true;
-
- // ---- error handling
- PasteboardCreateFailed: fprintf(stderr, "Cannot copy clipboard, PasteboardCreateFailed!\n");
- CFRelease(theClipboard);
- return false;
-}
-
-bool RetrieveBuffer(std::string& text, std::string::size_type& pos)
-{
- const int bufSize = 512;
- char buffer[bufSize];
-
- if (getClipBoard(buffer, bufSize))
- {
- text = buffer;
- pos += strlen(buffer);
- return true;
- }
- else
- {
- return false;
- }
-}
-
-#elif USE_X11
-static char* getSelection(Display *dpy, Window us, Atom selection)
-{
- int max_events = 50;
- Window owner = XGetSelectionOwner (dpy, selection);
- int ret;
-
- //printf("XConvertSelection on %s\n", XGetAtomName(dpy, selection));
- if (owner == None)
- {
- //printf("No owner\n");
- return NULL;
- }
- XConvertSelection(dpy, selection, XA_STRING, XA_PRIMARY, us, CurrentTime);
- XFlush(dpy);
-
- while (max_events--)
- {
- XEvent e;
-
- XNextEvent(dpy, &e);
- if(e.type == SelectionNotify)
- {
- //printf("Received %s\n", XGetAtomName(dpy, e.xselection.selection));
- if(e.xselection.property == None)
- {
- //printf("Couldn't convert\n");
- return NULL;
- }
-
- long unsigned len, left, dummy;
- int format;
- Atom type;
- unsigned char *data = NULL;
-
- XGetWindowProperty(dpy, us, e.xselection.property, 0, 0, False,
- AnyPropertyType, &type, &format, &len, &left, &data);
- if (left < 1)
- return NULL;
-
- ret = XGetWindowProperty(dpy, us, e.xselection.property, 0, left, False,
- AnyPropertyType, &type, &format, &len, &dummy, &data);
- if (ret != Success)
- {
- //printf("Failed to get property: %p on %lu\n", data, len);
- return NULL;
- }
-
- //printf(">>> Got %s: len=%lu left=%lu (event %i)\n", data, len, left, 50-max_events);
- return (char*)data;
- }
- }
- return NULL;
-}
-
-bool RetrieveBuffer(std::string& text, std::string::size_type& pos)
-{
- SDL_SysWMinfo info;
-
- //printf("Retrieving buffer...\n");
- SDL_VERSION(&info.version);
- if ( SDL_GetWMInfo(&info) )
- {
- Display *dpy = info.info.x11.display;
- Window us = info.info.x11.window;
- char *data = NULL;
-
- if (!data)
- {
- data = getSelection(dpy, us, XA_PRIMARY);
- }
- if (!data)
- {
- data = getSelection(dpy, us, XA_SECONDARY);
- }
- if (!data)
- {
- Atom XA_CLIPBOARD = XInternAtom(dpy, "CLIPBOARD", 0);
- data = getSelection(dpy, us, XA_CLIPBOARD);
- }
- if (data)
- {
- // check cursor position
- if (pos > text.size()) {
- pos = text.size();
- }
-
- text.insert(pos, data);
- pos += strlen(data);
- XFree(data);
-
- return true;
- }
- }
- return false;
+ char *buf = SDL_GetClipboardText();
+ const size_t len = strlen(buf);
+ if (len > 0) {
+ text.insert(pos, buf);
+ pos += len;
+ }
+ SDL_free(buf);
+ return len > 0;
}
-#else
-bool RetrieveBuffer(std::string&, std::string::size_type&) { return false; }
-#endif
diff --git a/src/utils/copynpaste.h b/src/utils/copynpaste.h
index c2430e1c..b6aa0de0 100644
--- a/src/utils/copynpaste.h
+++ b/src/utils/copynpaste.h
@@ -1,7 +1,6 @@
/*
- * Retrieve string pasted depending on OS mechanisms.
- * Copyright (C) 2001-2010 Wormux Team
- * Copyright (C) 2010-2012 The Mana Developers
+ * Clipboard Interaction.
+ * Copyright (C) 2010-2024 The Mana Developers
*
* This file is part of The Mana Client.
*
@@ -25,10 +24,7 @@
* Attempts to retrieve text from the clipboard buffer and inserts it in
* \a text at position \pos. The characters are encoded in utf-8.
*
- * Implemented for Windows, X11 and Mac OS X.
- *
* @return <code>true</code> when successful or <code>false</code> when there
* was a problem retrieving the clipboard buffer.
*/
-bool RetrieveBuffer(std::string& text, std::string::size_type& pos);
-
+bool insertFromClipboard(std::string &text, std::string::size_type &pos);
diff --git a/src/utils/dtor.h b/src/utils/dtor.h
index 223b73ed..76c68725 100644
--- a/src/utils/dtor.h
+++ b/src/utils/dtor.h
@@ -23,18 +23,16 @@
#define UTILS_DTOR_H
#include <algorithm>
-#include <functional>
#include <utility>
template<typename T>
-struct dtor : public std::unary_function <T, void>
+struct dtor
{
void operator()(T &ptr) { delete ptr; }
};
template<typename T1, typename T2>
-struct dtor<std::pair<T1, T2> > :
-public std::unary_function <std::pair<T1, T2>, void>
+struct dtor<std::pair<T1, T2>>
{
void operator()(std::pair<T1, T2> &pair) { delete pair.second; }
};
diff --git a/src/utils/mutex.h b/src/utils/mutex.h
index f7f26233..d0120cfa 100644
--- a/src/utils/mutex.h
+++ b/src/utils/mutex.h
@@ -53,9 +53,7 @@ class MutexLocker
{
public:
MutexLocker(Mutex *mutex);
-#ifdef ENABLE_CPP0X
MutexLocker(MutexLocker&&);
-#endif
~MutexLocker();
private:
@@ -95,13 +93,11 @@ inline MutexLocker::MutexLocker(Mutex *mutex):
mMutex->lock();
}
-#ifdef ENABLE_CPP0X
inline MutexLocker::MutexLocker(MutexLocker&& rhs):
mMutex(rhs.mMutex)
{
rhs.mMutex = NULL;
}
-#endif
inline MutexLocker::~MutexLocker()
{
diff --git a/src/utils/physfsrwops.h b/src/utils/physfsrwops.h
index 406fba6f..8008b224 100644
--- a/src/utils/physfsrwops.h
+++ b/src/utils/physfsrwops.h
@@ -40,7 +40,7 @@ extern "C" {
* @return A valid SDL_RWops structure on success, NULL on error. Specifics
* of the error can be gleaned from PHYSFS_getLastError().
*/
-__EXPORT__ SDL_RWops *PHYSFSRWOPS_openRead(const char *fname);
+SDL_RWops *PHYSFSRWOPS_openRead(const char *fname);
/**
* Open a platform-independent filename for writing, and make it accessible
@@ -52,7 +52,7 @@ __EXPORT__ SDL_RWops *PHYSFSRWOPS_openRead(const char *fname);
* @return A valid SDL_RWops structure on success, NULL on error. Specifics
* of the error can be gleaned from PHYSFS_getLastError().
*/
-__EXPORT__ SDL_RWops *PHYSFSRWOPS_openWrite(const char *fname);
+SDL_RWops *PHYSFSRWOPS_openWrite(const char *fname);
/**
* Open a platform-independent filename for appending, and make it accessible
@@ -64,7 +64,7 @@ __EXPORT__ SDL_RWops *PHYSFSRWOPS_openWrite(const char *fname);
* @return A valid SDL_RWops structure on success, NULL on error. Specifics
* of the error can be gleaned from PHYSFS_getLastError().
*/
-__EXPORT__ SDL_RWops *PHYSFSRWOPS_openAppend(const char *fname);
+SDL_RWops *PHYSFSRWOPS_openAppend(const char *fname);
/**
* Make a SDL_RWops from an existing PhysicsFS file handle. You should
@@ -76,7 +76,7 @@ __EXPORT__ SDL_RWops *PHYSFSRWOPS_openAppend(const char *fname);
* @return A valid SDL_RWops structure on success, NULL on error. Specifics
* of the error can be gleaned from PHYSFS_getLastError().
*/
-__EXPORT__ SDL_RWops *PHYSFSRWOPS_makeRWops(PHYSFS_File *handle);
+SDL_RWops *PHYSFSRWOPS_makeRWops(PHYSFS_File *handle);
#ifdef __cplusplus
}
@@ -85,4 +85,3 @@ __EXPORT__ SDL_RWops *PHYSFSRWOPS_makeRWops(PHYSFS_File *handle);
#endif /* include-once blocker */
/* end of physfsrwops.h ... */
-
diff --git a/src/utils/stringutils.cpp b/src/utils/stringutils.cpp
index 4f27d41b..05f1bf7b 100644
--- a/src/utils/stringutils.cpp
+++ b/src/utils/stringutils.cpp
@@ -136,7 +136,7 @@ int compareStrI(const std::string &a, const std::string &b)
std::string::const_iterator itB = b.begin();
std::string::const_iterator endB = b.end();
- for (; itA < endA, itB < endB; ++itA, ++itB)
+ for (; itA < endA && itB < endB; ++itA, ++itB)
{
int comp = tolower(*itA) - tolower(*itB);
if (comp)
diff --git a/src/vector.h b/src/vector.h
index d181f938..25f6c120 100644
--- a/src/vector.h
+++ b/src/vector.h
@@ -60,6 +60,14 @@ class Vector
return x == 0.0f && y == 0.0f && z == 0.0f;
}
+ Vector &operator=(const Vector &v)
+ {
+ x = v.x;
+ y = v.y;
+ z = v.z;
+ return *this;
+ }
+
/**
* Scale vector operator.
*/