mirror of
				https://github.com/edubart/otclient.git
				synced 2025-11-04 04:36:23 +01:00 
			
		
		
		
	Removed SDL2 and created JNI interface (Android Only)
This commit is contained in:
		@@ -132,6 +132,10 @@ set(framework_SOURCES ${framework_SOURCES}
 | 
			
		||||
    ${CMAKE_CURRENT_LIST_DIR}/platform/unixplatform.cpp
 | 
			
		||||
    ${CMAKE_CURRENT_LIST_DIR}/platform/platform.cpp
 | 
			
		||||
    ${CMAKE_CURRENT_LIST_DIR}/platform/platform.h
 | 
			
		||||
	
 | 
			
		||||
	# mobile
 | 
			
		||||
	${CMAKE_CURRENT_LIST_DIR}/platform/mobilefacade.cpp
 | 
			
		||||
	${CMAKE_CURRENT_LIST_DIR}/platform/mobilefacade.h
 | 
			
		||||
)
 | 
			
		||||
 | 
			
		||||
set_source_files_properties(${CMAKE_CURRENT_LIST_DIR}/luafunctions.cpp
 | 
			
		||||
@@ -232,7 +236,6 @@ find_package(ZLIB REQUIRED)
 | 
			
		||||
 | 
			
		||||
if(ANDROID)
 | 
			
		||||
    set(framework_LIBRARIES ${framework_LIBRARIES} android log)
 | 
			
		||||
    find_package(SDL2 REQUIRED)
 | 
			
		||||
endif()
 | 
			
		||||
 | 
			
		||||
set(framework_LIBRARIES ${framework_LIBRARIES}
 | 
			
		||||
@@ -252,8 +255,8 @@ set(framework_INCLUDE_DIRS ${framework_INCLUDE_DIRS}
 | 
			
		||||
)
 | 
			
		||||
 | 
			
		||||
if(ANDROID)
 | 
			
		||||
    set(framework_LIBRARIES ${framework_LIBRARIES} ${SDL2_LIBRARY})
 | 
			
		||||
    set(framework_INCLUDE_DIRS ${framework_INCLUDE_DIRS} ${SDL2_INCLUDE_DIR})
 | 
			
		||||
    set(framework_LIBRARIES ${framework_LIBRARIES})
 | 
			
		||||
    set(framework_INCLUDE_DIRS ${framework_INCLUDE_DIRS})
 | 
			
		||||
endif()
 | 
			
		||||
 | 
			
		||||
if(CMAKE_BUILD_TYPE STREQUAL "Debug" OR CMAKE_BUILD_TYPE STREQUAL "RelWithDebInfo")
 | 
			
		||||
@@ -459,8 +462,8 @@ if(FRAMEWORK_GRAPHICS)
 | 
			
		||||
        ${CMAKE_CURRENT_LIST_DIR}/platform/win32window.h
 | 
			
		||||
        ${CMAKE_CURRENT_LIST_DIR}/platform/x11window.cpp
 | 
			
		||||
        ${CMAKE_CURRENT_LIST_DIR}/platform/x11window.h
 | 
			
		||||
        ${CMAKE_CURRENT_LIST_DIR}/platform/sdlwindow.cpp
 | 
			
		||||
        ${CMAKE_CURRENT_LIST_DIR}/platform/sdlwindow.h
 | 
			
		||||
        ${CMAKE_CURRENT_LIST_DIR}/platform/androidwindow.cpp
 | 
			
		||||
        ${CMAKE_CURRENT_LIST_DIR}/platform/androidwindow.h
 | 
			
		||||
 | 
			
		||||
        # window input
 | 
			
		||||
        ${CMAKE_CURRENT_LIST_DIR}/input/mouse.cpp
 | 
			
		||||
 
 | 
			
		||||
@@ -177,6 +177,8 @@ std::string Application::getOs()
 | 
			
		||||
    return "mac";
 | 
			
		||||
#elif __linux
 | 
			
		||||
    return "linux";
 | 
			
		||||
#elif ANDROID
 | 
			
		||||
	return "android";
 | 
			
		||||
#else
 | 
			
		||||
    return "unknown";
 | 
			
		||||
#endif
 | 
			
		||||
 
 | 
			
		||||
@@ -45,7 +45,7 @@
 | 
			
		||||
#include "core/logger.h"
 | 
			
		||||
 | 
			
		||||
#ifdef ANDROID
 | 
			
		||||
#include <SDL.h>
 | 
			
		||||
#include "platform/mobilefacade.h"
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
#endif
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										506
									
								
								src/framework/platform/androidwindow.cpp
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										506
									
								
								src/framework/platform/androidwindow.cpp
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,506 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2010-2014 OTClient <https://github.com/edubart/otclient>
 | 
			
		||||
 *
 | 
			
		||||
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 | 
			
		||||
 * of this software and associated documentation files (the "Software"), to deal
 | 
			
		||||
 * in the Software without restriction, including without limitation the rights
 | 
			
		||||
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 | 
			
		||||
 * copies of the Software, and to permit persons to whom the Software is
 | 
			
		||||
 * furnished to do so, subject to the following conditions:
 | 
			
		||||
 *
 | 
			
		||||
 * The above copyright notice and this permission notice shall be included in
 | 
			
		||||
 * all copies or substantial portions of the Software.
 | 
			
		||||
 *
 | 
			
		||||
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 | 
			
		||||
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 | 
			
		||||
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 | 
			
		||||
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 | 
			
		||||
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 | 
			
		||||
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 | 
			
		||||
 * THE SOFTWARE.
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#ifdef ANDROID
 | 
			
		||||
 | 
			
		||||
#include "androidwindow.h"
 | 
			
		||||
 | 
			
		||||
AndroidWindow::AndroidWindow() {
 | 
			
		||||
    m_minimumSize = Size(600, 480);
 | 
			
		||||
    m_size = Size(600, 480);
 | 
			
		||||
    m_window = 0;
 | 
			
		||||
 | 
			
		||||
    m_keyMap[AndroidWindow::KEY_ENTER] = Fw::KeyEnter;
 | 
			
		||||
    m_keyMap[AndroidWindow::KEY_BACKSPACE] = Fw::KeyBackspace;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
AndroidWindow::~AndroidWindow() {
 | 
			
		||||
    JNIEnv* env = getJNIEnv();
 | 
			
		||||
    env->DeleteGlobalRef(m_nativeFacadeCalls);
 | 
			
		||||
 | 
			
		||||
    internalDestroyGLContext();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
AndroidWindow::KeyCode AndroidWindow::NativeEvent::getKeyCodeFromInt(int keyCode) {
 | 
			
		||||
    switch (keyCode) {
 | 
			
		||||
        case 66:
 | 
			
		||||
            return KEY_ENTER;
 | 
			
		||||
        case 67:
 | 
			
		||||
            return KEY_BACKSPACE;
 | 
			
		||||
        default:
 | 
			
		||||
            return KEY_UNDEFINED;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
AndroidWindow::EventType AndroidWindow::NativeEvent::getEventTypeFromInt(int actionType) {
 | 
			
		||||
    switch (actionType) {
 | 
			
		||||
        case 0:
 | 
			
		||||
            return TOUCH_DOWN;
 | 
			
		||||
        case 1:
 | 
			
		||||
            return TOUCH_UP;
 | 
			
		||||
        case 2:
 | 
			
		||||
            return TOUCH_MOTION;
 | 
			
		||||
        case 3:
 | 
			
		||||
            return TOUCH_LONGPRESS;
 | 
			
		||||
        default:
 | 
			
		||||
            return EVENT_UNDEFINED;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
JNIEnv* AndroidWindow::getJNIEnv() {
 | 
			
		||||
    JNIEnv *env;
 | 
			
		||||
 | 
			
		||||
    if (m_javaVM->AttachCurrentThread(&env, NULL) < 0) {
 | 
			
		||||
        g_logger.fatal("failed to attach current thread");
 | 
			
		||||
        return 0;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return env;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
std::string AndroidWindow::getStringFromJString( jstring text ) {
 | 
			
		||||
    JNIEnv* env = getJNIEnv();
 | 
			
		||||
 | 
			
		||||
    const char* newChar = env->GetStringUTFChars(text,NULL);
 | 
			
		||||
    std::string newText = newChar;
 | 
			
		||||
    env->ReleaseStringUTFChars(text, newChar);
 | 
			
		||||
 | 
			
		||||
    return newText;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::getJavaSurfaceAndSet() {
 | 
			
		||||
    jobject nativeWindowObject;
 | 
			
		||||
    JNIEnv* env = getJNIEnv();
 | 
			
		||||
 | 
			
		||||
    nativeWindowObject = env->CallStaticObjectMethod(m_nativeFacadeCalls, m_midGetNativeSurface);
 | 
			
		||||
    m_window = ANativeWindow_fromSurface(env, nativeWindowObject);
 | 
			
		||||
    env->DeleteLocalRef(nativeWindowObject);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::internalInitGL() {
 | 
			
		||||
    internalCheckGL();
 | 
			
		||||
    internalChooseGL();
 | 
			
		||||
    internalConnectGLContext();
 | 
			
		||||
    internalCreateGLContext();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::internalCheckGL() {
 | 
			
		||||
    m_eglDisplay = eglGetDisplay(EGL_DEFAULT_DISPLAY);
 | 
			
		||||
    if(m_eglDisplay == EGL_NO_DISPLAY)
 | 
			
		||||
        g_logger.fatal("EGL not supported");
 | 
			
		||||
 | 
			
		||||
    if(!eglInitialize(m_eglDisplay, NULL, NULL))
 | 
			
		||||
        g_logger.fatal("Unable to initialize EGL");
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::internalChooseGL() {
 | 
			
		||||
    static int attrList[] = {
 | 
			
		||||
#if OPENGL_ES==2
 | 
			
		||||
        EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT,
 | 
			
		||||
#else
 | 
			
		||||
        EGL_RENDERABLE_TYPE, EGL_OPENGL_ES_BIT,
 | 
			
		||||
#endif
 | 
			
		||||
        EGL_RED_SIZE, 4,
 | 
			
		||||
        EGL_GREEN_SIZE, 4,
 | 
			
		||||
        EGL_BLUE_SIZE, 4,
 | 
			
		||||
        EGL_ALPHA_SIZE, 4,
 | 
			
		||||
        EGL_NONE
 | 
			
		||||
    };
 | 
			
		||||
 | 
			
		||||
    EGLint numConfig;
 | 
			
		||||
 | 
			
		||||
    if(!eglChooseConfig(m_eglDisplay, attrList, &m_eglConfig, 1, &numConfig))
 | 
			
		||||
        g_logger.fatal("Failed to choose EGL config");
 | 
			
		||||
 | 
			
		||||
    if(numConfig != 1)
 | 
			
		||||
        g_logger.warning("Didn't got the exact EGL config");
 | 
			
		||||
 | 
			
		||||
    EGLint vid;
 | 
			
		||||
    if(!eglGetConfigAttrib(m_eglDisplay, m_eglConfig, EGL_NATIVE_VISUAL_ID, &vid))
 | 
			
		||||
        g_logger.fatal("Unable to get visual EGL visual id");
 | 
			
		||||
 | 
			
		||||
    ANativeWindow_setBuffersGeometry(m_window, 0, 0, vid);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::internalCreateGLContext() {
 | 
			
		||||
    EGLint attrList[] = {
 | 
			
		||||
#if OPENGL_ES==2
 | 
			
		||||
        EGL_CONTEXT_CLIENT_VERSION, 2,
 | 
			
		||||
#else
 | 
			
		||||
        EGL_CONTEXT_CLIENT_VERSION, 1,
 | 
			
		||||
#endif
 | 
			
		||||
        EGL_NONE
 | 
			
		||||
    };
 | 
			
		||||
 | 
			
		||||
    m_eglContext = eglCreateContext(m_eglDisplay, m_eglConfig, EGL_NO_CONTEXT, attrList);
 | 
			
		||||
    if(m_eglContext == EGL_NO_CONTEXT )
 | 
			
		||||
        g_logger.fatal(stdext::format("Unable to create EGL context: %s", eglGetError()));
 | 
			
		||||
 | 
			
		||||
    if (!eglMakeCurrent(m_eglDisplay, m_eglSurface, m_eglSurface, m_eglContext))
 | 
			
		||||
        g_logger.fatal("Unable to connect EGL context into Android native window");
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::internalDestroyGLContext() {
 | 
			
		||||
    if (m_window == NULL)
 | 
			
		||||
        return;
 | 
			
		||||
 | 
			
		||||
    if(m_eglDisplay) {
 | 
			
		||||
        eglMakeCurrent(m_eglDisplay, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT);
 | 
			
		||||
 | 
			
		||||
        if (m_eglSurface) {
 | 
			
		||||
            eglDestroySurface(m_eglDisplay, m_eglSurface);
 | 
			
		||||
            m_eglSurface = EGL_NO_SURFACE;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if(m_eglContext) {
 | 
			
		||||
            eglDestroyContext(m_eglDisplay, m_eglContext);
 | 
			
		||||
            m_eglContext = EGL_NO_CONTEXT;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        eglTerminate(m_eglDisplay);
 | 
			
		||||
        m_eglDisplay = EGL_NO_DISPLAY;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::internalConnectGLContext() {
 | 
			
		||||
    m_eglSurface = eglCreateWindowSurface(m_eglDisplay, m_eglConfig, m_window, NULL);
 | 
			
		||||
    if(m_eglSurface == EGL_NO_SURFACE)
 | 
			
		||||
        g_logger.fatal(stdext::format("Unable to create EGL surface: %s", eglGetError()));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::terminate() {
 | 
			
		||||
    nativePause();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::poll() {
 | 
			
		||||
    handleNativeEvents();
 | 
			
		||||
 | 
			
		||||
    while( !m_events.empty() ) {
 | 
			
		||||
        m_currentEvent = m_events.front();
 | 
			
		||||
 | 
			
		||||
        processKeyDownOrKeyUp();
 | 
			
		||||
 | 
			
		||||
        switch( m_currentEvent.type ) {
 | 
			
		||||
            case TEXTINPUT:
 | 
			
		||||
                processTextInput();
 | 
			
		||||
                break;
 | 
			
		||||
            case TOUCH_DOWN:
 | 
			
		||||
            case TOUCH_LONGPRESS:
 | 
			
		||||
            case TOUCH_UP:
 | 
			
		||||
                processFingerdownAndFingerup();
 | 
			
		||||
                break;
 | 
			
		||||
            case TOUCH_MOTION:
 | 
			
		||||
                processFingermotion();
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        m_events.pop();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    fireKeysPress();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::processKeyDownOrKeyUp() {
 | 
			
		||||
    if(m_currentEvent.type == KEY_DOWN || m_currentEvent.type == KEY_UP) {
 | 
			
		||||
        Fw::Key keyCode = Fw::KeyUnknown;
 | 
			
		||||
        KeyCode key = m_currentEvent.keyCode;
 | 
			
		||||
 | 
			
		||||
        if(m_keyMap.find(key) != m_keyMap.end())
 | 
			
		||||
            keyCode = m_keyMap[key];
 | 
			
		||||
 | 
			
		||||
        if(m_currentEvent.type == KEY_DOWN)
 | 
			
		||||
            processKeyDown(keyCode);
 | 
			
		||||
        else if(m_currentEvent.type == KEY_UP)
 | 
			
		||||
            processKeyUp(keyCode);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::processTextInput() {
 | 
			
		||||
    std::string text = m_currentEvent.text;
 | 
			
		||||
    KeyCode keyCode = m_currentEvent.keyCode;
 | 
			
		||||
 | 
			
		||||
    if(text.length() == 0 || keyCode == KEY_ENTER || keyCode == KEY_BACKSPACE)
 | 
			
		||||
        return;
 | 
			
		||||
 | 
			
		||||
    if(m_onInputEvent) {
 | 
			
		||||
        m_inputEvent.reset(Fw::KeyTextInputEvent);
 | 
			
		||||
        m_inputEvent.keyText = text;
 | 
			
		||||
        m_onInputEvent(m_inputEvent);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::processFingerdownAndFingerup() {
 | 
			
		||||
    bool isTouchdown = m_currentEvent.type == TOUCH_DOWN;
 | 
			
		||||
    Fw::MouseButton mouseButton = (m_currentEvent.type == TOUCH_LONGPRESS) ?
 | 
			
		||||
        Fw::MouseRightButton : Fw::MouseLeftButton;
 | 
			
		||||
 | 
			
		||||
    m_inputEvent.reset();
 | 
			
		||||
    m_inputEvent.type = (isTouchdown) ? Fw::MousePressInputEvent : Fw::MouseReleaseInputEvent;
 | 
			
		||||
    m_inputEvent.mouseButton = Fw::MouseLeftButton;
 | 
			
		||||
    m_mouseButtonStates[mouseButton] = isTouchdown;
 | 
			
		||||
 | 
			
		||||
    Point newMousePos(m_currentEvent.x, m_currentEvent.y);
 | 
			
		||||
    m_inputEvent.mouseMoved = newMousePos - m_inputEvent.mousePos;
 | 
			
		||||
    m_inputEvent.mousePos = newMousePos;
 | 
			
		||||
 | 
			
		||||
    if(m_onInputEvent)
 | 
			
		||||
        m_onInputEvent(m_inputEvent);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::processFingermotion() {
 | 
			
		||||
    m_inputEvent.reset();
 | 
			
		||||
    m_inputEvent.type = Fw::MouseMoveInputEvent;
 | 
			
		||||
 | 
			
		||||
    Point newMousePos(m_currentEvent.x, m_currentEvent.y);
 | 
			
		||||
    m_inputEvent.mouseMoved = newMousePos - m_inputEvent.mousePos;
 | 
			
		||||
    m_inputEvent.mousePos = newMousePos;
 | 
			
		||||
 | 
			
		||||
    if (m_onInputEvent)
 | 
			
		||||
        m_onInputEvent(m_inputEvent);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::swapBuffers() {
 | 
			
		||||
    eglSwapBuffers(m_eglDisplay, m_eglSurface);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::setVerticalSync(bool enable) {
 | 
			
		||||
    eglSwapInterval(m_eglDisplay, enable ? 1 : 0);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
std::string AndroidWindow::getClipboardText() {
 | 
			
		||||
    // TODO
 | 
			
		||||
    return "";
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::setClipboardText(const std::string& text) {
 | 
			
		||||
    // TODO
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
Size AndroidWindow::getDisplaySize() {
 | 
			
		||||
    return m_size;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
std::string AndroidWindow::getPlatformType() {
 | 
			
		||||
    return "ANDROID-EGL";
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::init() {
 | 
			
		||||
    internalInitGL();
 | 
			
		||||
    nativeResume();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::show() {}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::hide() {}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::maximize() {}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::move(const Point& pos) {}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::resize(const Size& size) {}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::showMouse() {}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::hideMouse() {}
 | 
			
		||||
 | 
			
		||||
int AndroidWindow::internalLoadMouseCursor(const ImagePtr& image, const Point& hotSpot) {
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::setMouseCursor(int cursorId) {}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::restoreMouseCursor() {}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::setTitle(const std::string& title) {}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::setMinimumSize(const Size& minimumSize) {}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::setFullscreen(bool fullscreen) {}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::setIcon(const std::string& iconFile) {}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::initializeJNI(JNIEnv* env) {
 | 
			
		||||
    env->GetJavaVM(&m_javaVM);
 | 
			
		||||
    env = getJNIEnv();
 | 
			
		||||
 | 
			
		||||
    jclass temp = m_nativeFacadeCalls = env->FindClass(
 | 
			
		||||
        "com/otclient/mobile/NativeFacadeCalls");
 | 
			
		||||
    m_nativeFacadeCalls = (jclass)env->NewGlobalRef(temp);
 | 
			
		||||
 | 
			
		||||
    m_midGetNativeSurface = env->GetStaticMethodID(m_nativeFacadeCalls,
 | 
			
		||||
        "getNativeSurface", "()Landroid/view/Surface;");
 | 
			
		||||
 | 
			
		||||
    m_midShowKeyboardSoft = env->GetStaticMethodID(m_nativeFacadeCalls,
 | 
			
		||||
        "showKeyboardSoft", "()V");
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::nativePause() {
 | 
			
		||||
    m_visible = false;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::nativeResume() {
 | 
			
		||||
    m_visible = true;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::nativeDestroy() {
 | 
			
		||||
    m_messages.push(APP_TERMINATE);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::onNativeResize(int width, int height) {
 | 
			
		||||
    m_size = Size(width, height);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::nativeCommitText(jstring jString) {
 | 
			
		||||
    std::string text = getStringFromJString(jString);
 | 
			
		||||
 | 
			
		||||
    m_events.push(NativeEvent(TEXTINPUT, text));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::onNativeSurfaceChanged() {
 | 
			
		||||
    if( m_eglSurface == EGL_NO_SURFACE ) {
 | 
			
		||||
        if( m_window )
 | 
			
		||||
            ANativeWindow_release(m_window);
 | 
			
		||||
 | 
			
		||||
        getJavaSurfaceAndSet();
 | 
			
		||||
                
 | 
			
		||||
        m_messages.push(RECREATE_CONTEXT);
 | 
			
		||||
 | 
			
		||||
        nativeResume();
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::onNativeSurfaceDestroyed() {
 | 
			
		||||
    internalDestroyGLContext();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::onNativeTouch(int actionType,
 | 
			
		||||
                            float x, float y) {
 | 
			
		||||
    EventType type = NativeEvent::getEventTypeFromInt(actionType);
 | 
			
		||||
    
 | 
			
		||||
    m_events.push(NativeEvent(type, x, y));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::onNativeKeyDown( int keyCode ) {
 | 
			
		||||
    KeyCode key = NativeEvent::getKeyCodeFromInt(keyCode);
 | 
			
		||||
    
 | 
			
		||||
    m_events.push(NativeEvent(KEY_DOWN, key));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::onNativeKeyUp( int keyCode ) {
 | 
			
		||||
    KeyCode key = NativeEvent::getKeyCodeFromInt(keyCode);
 | 
			
		||||
 | 
			
		||||
    m_events.push(NativeEvent(KEY_UP, key));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// these events need to be processed on native thread.
 | 
			
		||||
void AndroidWindow::handleNativeEvents() {
 | 
			
		||||
    NativeMessage nativeMessage;
 | 
			
		||||
 | 
			
		||||
    while (!m_messages.empty()) {
 | 
			
		||||
        nativeMessage = m_messages.front();
 | 
			
		||||
 | 
			
		||||
        switch (nativeMessage) {
 | 
			
		||||
            case RECREATE_CONTEXT:
 | 
			
		||||
                if(!m_eglContext)
 | 
			
		||||
                    internalInitGL();
 | 
			
		||||
                break;
 | 
			
		||||
            case APP_TERMINATE:
 | 
			
		||||
                raise(SIGTERM);
 | 
			
		||||
                break;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        m_messages.pop();
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void AndroidWindow::showKeyboardSoft() {
 | 
			
		||||
    JNIEnv* env = getJNIEnv();
 | 
			
		||||
    env->CallStaticVoidMethod(m_nativeFacadeCalls, m_midShowKeyboardSoft);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/*
 | 
			
		||||
 * Java JNI functions
 | 
			
		||||
*/
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_MainActivity_nativeInit(
 | 
			
		||||
    JNIEnv* env, jobject obj) {
 | 
			
		||||
    ((AndroidWindow&)g_window).initializeJNI(env);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_MainActivity_nativePause(
 | 
			
		||||
    JNIEnv* env, jobject obj) {
 | 
			
		||||
    ((AndroidWindow&)g_window).nativePause();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_MainActivity_nativeResume(
 | 
			
		||||
    JNIEnv* env, jobject obj) {
 | 
			
		||||
    ((AndroidWindow&)g_window).nativeResume();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_MainActivity_nativeDestroy(
 | 
			
		||||
    JNIEnv* env, jobject obj) {
 | 
			
		||||
    ((AndroidWindow&)g_window).nativeDestroy();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_NativeSurfaceView_onNativeResize(
 | 
			
		||||
    JNIEnv*, jobject, jint width, jint height) {
 | 
			
		||||
    ((AndroidWindow&)g_window).onNativeResize(width, height);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_NativeSurfaceView_onNativeSurfaceChanged(
 | 
			
		||||
        JNIEnv* env, jobject obj) {
 | 
			
		||||
    ((AndroidWindow&) g_window).onNativeSurfaceChanged();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_NativeSurfaceView_onNativeSurfaceDestroyed(
 | 
			
		||||
    JNIEnv* env, jobject obj) {
 | 
			
		||||
    ((AndroidWindow&)g_window).onNativeSurfaceDestroyed();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_NativeSurfaceView_onNativeTouch(
 | 
			
		||||
        JNIEnv* env, jobject obj, jint actionType, jfloat x, jfloat y) {
 | 
			
		||||
    ((AndroidWindow&) g_window).onNativeTouch(actionType, x, y);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_InputConnectionForNative_nativeCommitText(
 | 
			
		||||
        JNIEnv* env, jobject obj, jstring text ) {
 | 
			
		||||
    ((AndroidWindow&) g_window).nativeCommitText(text);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_FakeEditText_onNativeKeyDown(
 | 
			
		||||
        JNIEnv* env, jobject obj, jint keyCode ) {
 | 
			
		||||
    ((AndroidWindow&) g_window).onNativeKeyDown(keyCode);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_FakeEditText_onNativeKeyUp(
 | 
			
		||||
        JNIEnv* env, jobject obj, jint keyCode ) {
 | 
			
		||||
    ((AndroidWindow&) g_window).onNativeKeyUp(keyCode);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_NativeMainThread_nativeStartApp(
 | 
			
		||||
        JNIEnv*, jobject ) {
 | 
			
		||||
    char *argv[2];
 | 
			
		||||
    argv[0] = strdup("OTClient");
 | 
			
		||||
    argv[1] = NULL;
 | 
			
		||||
    main(1, argv);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#endif // ANDROID
 | 
			
		||||
							
								
								
									
										201
									
								
								src/framework/platform/androidwindow.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										201
									
								
								src/framework/platform/androidwindow.h
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,201 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2010-2014 OTClient <https://github.com/edubart/otclient>
 | 
			
		||||
 *
 | 
			
		||||
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 | 
			
		||||
 * of this software and associated documentation files (the "Software"), to deal
 | 
			
		||||
 * in the Software without restriction, including without limitation the rights
 | 
			
		||||
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 | 
			
		||||
 * copies of the Software, and to permit persons to whom the Software is
 | 
			
		||||
 * furnished to do so, subject to the following conditions:
 | 
			
		||||
 *
 | 
			
		||||
 * The above copyright notice and this permission notice shall be included in
 | 
			
		||||
 * all copies or substantial portions of the Software.
 | 
			
		||||
 *
 | 
			
		||||
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 | 
			
		||||
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 | 
			
		||||
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 | 
			
		||||
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 | 
			
		||||
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 | 
			
		||||
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 | 
			
		||||
 * THE SOFTWARE.
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#ifndef ANDROIDWINDOW_H
 | 
			
		||||
#define ANDROIDWINDOW_H
 | 
			
		||||
 | 
			
		||||
#include "platformwindow.h"
 | 
			
		||||
#include <android/native_window.h>
 | 
			
		||||
#include <android/native_window_jni.h>
 | 
			
		||||
#include <jni.h>
 | 
			
		||||
#include <EGL/egl.h>
 | 
			
		||||
#include <queue>
 | 
			
		||||
 | 
			
		||||
class AndroidWindow : public PlatformWindow
 | 
			
		||||
{
 | 
			
		||||
    enum KeyCode {
 | 
			
		||||
        KEY_UNDEFINED,
 | 
			
		||||
        KEY_BACKSPACE = 66,
 | 
			
		||||
        KEY_ENTER = 67
 | 
			
		||||
    };
 | 
			
		||||
 | 
			
		||||
    enum EventType {
 | 
			
		||||
        TOUCH_DOWN,
 | 
			
		||||
        TOUCH_UP,
 | 
			
		||||
        TOUCH_MOTION,
 | 
			
		||||
        TOUCH_LONGPRESS,
 | 
			
		||||
        KEY_DOWN,
 | 
			
		||||
        KEY_UP,
 | 
			
		||||
        TEXTINPUT,
 | 
			
		||||
        EVENT_UNDEFINED
 | 
			
		||||
    };
 | 
			
		||||
 | 
			
		||||
    enum NativeMessage {
 | 
			
		||||
        RECREATE_CONTEXT,
 | 
			
		||||
        APP_TERMINATE
 | 
			
		||||
    };
 | 
			
		||||
 | 
			
		||||
    struct NativeEvent {
 | 
			
		||||
        NativeEvent() {}
 | 
			
		||||
 | 
			
		||||
        NativeEvent(EventType type, float x, float y) :
 | 
			
		||||
            type(type), text(""), keyCode(KEY_UNDEFINED), x(x), y(y) {}
 | 
			
		||||
 | 
			
		||||
        NativeEvent(EventType type, std::string text) :
 | 
			
		||||
            type(type), text(text), keyCode(KEY_UNDEFINED), x(0), y(0) {}
 | 
			
		||||
 | 
			
		||||
        NativeEvent(EventType type, KeyCode keyCode) :
 | 
			
		||||
            type(type), text(""), keyCode(keyCode), x(0), y(0) {}
 | 
			
		||||
 | 
			
		||||
        static KeyCode getKeyCodeFromInt(int);
 | 
			
		||||
        static EventType getEventTypeFromInt(int);
 | 
			
		||||
 | 
			
		||||
        EventType type;
 | 
			
		||||
        std::string text;
 | 
			
		||||
        KeyCode keyCode;
 | 
			
		||||
        float x;
 | 
			
		||||
        float y;
 | 
			
		||||
    };
 | 
			
		||||
 | 
			
		||||
    void internalInitGL();
 | 
			
		||||
    void internalCheckGL();
 | 
			
		||||
    void internalChooseGL();
 | 
			
		||||
    void internalCreateGLContext();
 | 
			
		||||
    void internalDestroyGLContext();
 | 
			
		||||
    void internalConnectGLContext();
 | 
			
		||||
 | 
			
		||||
    void processKeyDownOrKeyUp();
 | 
			
		||||
    void processTextInput();
 | 
			
		||||
    void processFingerdownAndFingerup();
 | 
			
		||||
    void processFingermotion();
 | 
			
		||||
 | 
			
		||||
    void handleNativeEvents();
 | 
			
		||||
 | 
			
		||||
    JNIEnv* getJNIEnv();
 | 
			
		||||
    std::string getStringFromJString( jstring );
 | 
			
		||||
 | 
			
		||||
    // JNI Java calls
 | 
			
		||||
    void getJavaSurfaceAndSet();
 | 
			
		||||
public:
 | 
			
		||||
    AndroidWindow();
 | 
			
		||||
    ~AndroidWindow();
 | 
			
		||||
 | 
			
		||||
    void init();
 | 
			
		||||
    void terminate();
 | 
			
		||||
 | 
			
		||||
    void move(const Point& pos);
 | 
			
		||||
    void resize(const Size& size);
 | 
			
		||||
    void show();
 | 
			
		||||
    void hide();
 | 
			
		||||
    void maximize();
 | 
			
		||||
    void poll();
 | 
			
		||||
    void swapBuffers();
 | 
			
		||||
    void showMouse();
 | 
			
		||||
    void hideMouse();
 | 
			
		||||
 | 
			
		||||
    void setMouseCursor(int cursorId);
 | 
			
		||||
    void restoreMouseCursor();
 | 
			
		||||
 | 
			
		||||
    void setTitle(const std::string& title);
 | 
			
		||||
    void setMinimumSize(const Size& minimumSize);
 | 
			
		||||
    void setFullscreen(bool fullscreen);
 | 
			
		||||
    void setVerticalSync(bool enable);
 | 
			
		||||
    void setIcon(const std::string& iconFile);
 | 
			
		||||
    void setClipboardText(const std::string& text);
 | 
			
		||||
 | 
			
		||||
    Size getDisplaySize();
 | 
			
		||||
    std::string getClipboardText();
 | 
			
		||||
    std::string getPlatformType();
 | 
			
		||||
 | 
			
		||||
    void initializeJNI(JNIEnv*);
 | 
			
		||||
    void nativePause();
 | 
			
		||||
    void nativeResume();
 | 
			
		||||
    void nativeDestroy();
 | 
			
		||||
    void onNativeResize(int, int);
 | 
			
		||||
    void onNativeSurfaceChanged();
 | 
			
		||||
    void onNativeSurfaceDestroyed();
 | 
			
		||||
    void onNativeTouch(int actionType, float x, float y);
 | 
			
		||||
    void nativeCommitText(jstring);
 | 
			
		||||
    void onNativeKeyDown(int);
 | 
			
		||||
    void onNativeKeyUp(int);
 | 
			
		||||
    void showKeyboardSoft();
 | 
			
		||||
protected:
 | 
			
		||||
    int internalLoadMouseCursor(const ImagePtr& image, const Point& hotSpot);
 | 
			
		||||
private:
 | 
			
		||||
    JavaVM* m_javaVM;
 | 
			
		||||
    ANativeWindow* m_window;
 | 
			
		||||
    jclass m_nativeFacadeCalls;
 | 
			
		||||
    jmethodID m_midGetNativeSurface;
 | 
			
		||||
    jmethodID m_midShowKeyboardSoft;
 | 
			
		||||
 | 
			
		||||
    EGLConfig m_eglConfig;
 | 
			
		||||
    EGLContext m_eglContext;
 | 
			
		||||
    EGLDisplay m_eglDisplay;
 | 
			
		||||
    EGLSurface m_eglSurface;
 | 
			
		||||
 | 
			
		||||
    std::queue<NativeEvent> m_events;
 | 
			
		||||
    std::queue<NativeMessage> m_messages;
 | 
			
		||||
    NativeEvent m_currentEvent;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
extern "C" {
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_NativeMainThread_nativeStartApp(
 | 
			
		||||
    JNIEnv*, jobject);
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_MainActivity_nativeInit(
 | 
			
		||||
    JNIEnv*, jobject);
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_MainActivity_nativeResume(
 | 
			
		||||
    JNIEnv*, jobject);
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_MainActivity_nativePause(
 | 
			
		||||
    JNIEnv*, jobject);
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_MainActivity_nativeDestroy(
 | 
			
		||||
    JNIEnv*, jobject);
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_NativeSurfaceView_onNativeResize(
 | 
			
		||||
    JNIEnv*, jobject, jint, jint);
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_NativeSurfaceView_onNativeSurfaceChanged(
 | 
			
		||||
    JNIEnv*, jobject);
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_NativeSurfaceView_onNativeSurfaceDestroyed(
 | 
			
		||||
    JNIEnv*, jobject);
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_NativeSurfaceView_onNativeTouch(
 | 
			
		||||
    JNIEnv* env, jobject obj, jint actionType, jfloat x, jfloat y);
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_InputConnectionForNative_nativeCommitText(
 | 
			
		||||
    JNIEnv*, jobject, jstring );
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_FakeEditText_onNativeKeyDown(
 | 
			
		||||
    JNIEnv*, jobject, jint );
 | 
			
		||||
 | 
			
		||||
void Java_com_otclient_mobile_FakeEditText_onNativeKeyUp(
 | 
			
		||||
    JNIEnv*, jobject, jint );
 | 
			
		||||
 | 
			
		||||
int main(int, char* argv[]);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#endif
 | 
			
		||||
							
								
								
									
										30
									
								
								src/framework/platform/mobilefacade.cpp
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										30
									
								
								src/framework/platform/mobilefacade.cpp
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,30 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2010-2014 OTClient <https://github.com/edubart/otclient>
 | 
			
		||||
 *
 | 
			
		||||
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 | 
			
		||||
 * of this software and associated documentation files (the "Software"), to deal
 | 
			
		||||
 * in the Software without restriction, including without limitation the rights
 | 
			
		||||
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 | 
			
		||||
 * copies of the Software, and to permit persons to whom the Software is
 | 
			
		||||
 * furnished to do so, subject to the following conditions:
 | 
			
		||||
 *
 | 
			
		||||
 * The above copyright notice and this permission notice shall be included in
 | 
			
		||||
 * all copies or substantial portions of the Software.
 | 
			
		||||
 *
 | 
			
		||||
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 | 
			
		||||
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 | 
			
		||||
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 | 
			
		||||
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 | 
			
		||||
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 | 
			
		||||
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 | 
			
		||||
 * THE SOFTWARE.
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include "mobilefacade.h"
 | 
			
		||||
#include "androidwindow.h"
 | 
			
		||||
 | 
			
		||||
MobileFacade g_mobileFacade;
 | 
			
		||||
 | 
			
		||||
void MobileFacade::showKeyboardSoft() {
 | 
			
		||||
    ((AndroidWindow&) g_window).showKeyboardSoft();
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										33
									
								
								src/framework/platform/mobilefacade.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										33
									
								
								src/framework/platform/mobilefacade.h
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,33 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2010-2014 OTClient <https://github.com/edubart/otclient>
 | 
			
		||||
 *
 | 
			
		||||
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 | 
			
		||||
 * of this software and associated documentation files (the "Software"), to deal
 | 
			
		||||
 * in the Software without restriction, including without limitation the rights
 | 
			
		||||
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 | 
			
		||||
 * copies of the Software, and to permit persons to whom the Software is
 | 
			
		||||
 * furnished to do so, subject to the following conditions:
 | 
			
		||||
 *
 | 
			
		||||
 * The above copyright notice and this permission notice shall be included in
 | 
			
		||||
 * all copies or substantial portions of the Software.
 | 
			
		||||
 *
 | 
			
		||||
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 | 
			
		||||
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 | 
			
		||||
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 | 
			
		||||
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 | 
			
		||||
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 | 
			
		||||
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 | 
			
		||||
 * THE SOFTWARE.
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#ifndef MOBILEFACADE_H
 | 
			
		||||
#define MOBILEFACADE_H
 | 
			
		||||
 | 
			
		||||
class MobileFacade {
 | 
			
		||||
public:
 | 
			
		||||
    void showKeyboardSoft();
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
extern MobileFacade g_mobileFacade;
 | 
			
		||||
 | 
			
		||||
#endif
 | 
			
		||||
@@ -26,8 +26,8 @@
 | 
			
		||||
#include "win32window.h"
 | 
			
		||||
WIN32Window window;
 | 
			
		||||
#elif defined ANDROID
 | 
			
		||||
#include "sdlwindow.h"
 | 
			
		||||
SDLWindow window;
 | 
			
		||||
#include "androidwindow.h"
 | 
			
		||||
AndroidWindow window;
 | 
			
		||||
#else
 | 
			
		||||
#include "x11window.h"
 | 
			
		||||
#include <framework/core/clock.h>
 | 
			
		||||
 
 | 
			
		||||
@@ -1,383 +0,0 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2010-2014 OTClient <https://github.com/edubart/otclient>
 | 
			
		||||
 *
 | 
			
		||||
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 | 
			
		||||
 * of this software and associated documentation files (the "Software"), to deal
 | 
			
		||||
 * in the Software without restriction, including without limitation the rights
 | 
			
		||||
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 | 
			
		||||
 * copies of the Software, and to permit persons to whom the Software is
 | 
			
		||||
 * furnished to do so, subject to the following conditions:
 | 
			
		||||
 *
 | 
			
		||||
 * The above copyright notice and this permission notice shall be included in
 | 
			
		||||
 * all copies or substantial portions of the Software.
 | 
			
		||||
 *
 | 
			
		||||
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 | 
			
		||||
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 | 
			
		||||
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 | 
			
		||||
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 | 
			
		||||
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 | 
			
		||||
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 | 
			
		||||
 * THE SOFTWARE.
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#ifdef ANDROID
 | 
			
		||||
 | 
			
		||||
#include "sdlwindow.h"
 | 
			
		||||
 | 
			
		||||
SDLWindow::SDLWindow() {
 | 
			
		||||
    m_minimumSize = Size(600,480);
 | 
			
		||||
    m_size = Size(600,480);
 | 
			
		||||
    m_window = 0;
 | 
			
		||||
 | 
			
		||||
    //m_keyMap[SDLK_ESCAPE] = Fw::KeyEscape;
 | 
			
		||||
    //m_keyMap[SDLK_TAB] = Fw::KeyTab;
 | 
			
		||||
    m_keyMap[SDLK_RETURN] = Fw::KeyEnter;
 | 
			
		||||
    m_keyMap[SDLK_BACKSPACE] = Fw::KeyBackspace;
 | 
			
		||||
    m_keyMap[SDLK_SPACE] = Fw::KeySpace;
 | 
			
		||||
 | 
			
		||||
    /*
 | 
			
		||||
    m_keyMap[SDLK_PAGEUP] = Fw::KeyPageUp;
 | 
			
		||||
    m_keyMap[SDLK_PAGEDOWN] = Fw::KeyPageDown;
 | 
			
		||||
    m_keyMap[SDLK_HOME] = Fw::KeyHome;
 | 
			
		||||
    m_keyMap[SDLK_END] = Fw::KeyEnd;
 | 
			
		||||
    m_keyMap[SDLK_INSERT] = Fw::KeyInsert;
 | 
			
		||||
    m_keyMap[SDLK_DELETE] = Fw::KeyDelete;
 | 
			
		||||
 | 
			
		||||
    m_keyMap[SDLK_UP] = Fw::KeyUp;
 | 
			
		||||
    m_keyMap[SDLK_DOWN] = Fw::KeyDown;
 | 
			
		||||
    m_keyMap[SDLK_LEFT] = Fw::KeyLeft;
 | 
			
		||||
    m_keyMap[SDLK_RIGHT] = Fw::KeyRight;
 | 
			
		||||
 | 
			
		||||
    m_keyMap[SDLK_NUMLOCKCLEAR] = Fw::KeyNumLock;
 | 
			
		||||
    m_keyMap[SDLK_SCROLLLOCK] = Fw::KeyScrollLock;
 | 
			
		||||
    m_keyMap[SDLK_CAPSLOCK] = Fw::KeyCapsLock;
 | 
			
		||||
    m_keyMap[SDLK_PRINTSCREEN] = Fw::KeyPrintScreen;
 | 
			
		||||
    m_keyMap[SDLK_PAUSE] = Fw::KeyPause;
 | 
			
		||||
 | 
			
		||||
    m_keyMap[SDLK_LCTRL] = Fw::KeyCtrl;
 | 
			
		||||
    m_keyMap[SDLK_RCTRL] = Fw::KeyCtrl;
 | 
			
		||||
    m_keyMap[SDLK_LSHIFT] = Fw::KeyShift;
 | 
			
		||||
    m_keyMap[SDLK_RSHIFT] = Fw::KeyShift;
 | 
			
		||||
    m_keyMap[SDLK_LALT] = Fw::KeyAlt;
 | 
			
		||||
    m_keyMap[SDLK_RALT] = Fw::KeyAlt;
 | 
			
		||||
    m_keyMap[SDLK_LGUI] = Fw::KeyMeta;
 | 
			
		||||
    m_keyMap[SDLK_RGUI] = Fw::KeyMeta;
 | 
			
		||||
    */
 | 
			
		||||
 | 
			
		||||
    // ascii characters
 | 
			
		||||
    m_keyMap[SDLK_EXCLAIM] = Fw::KeyExclamation;
 | 
			
		||||
    m_keyMap[SDLK_QUOTEDBL] = Fw::KeyQuote;
 | 
			
		||||
    m_keyMap[SDLK_HASH] = Fw::KeyNumberSign;
 | 
			
		||||
    m_keyMap[SDLK_DOLLAR] = Fw::KeyDollar;
 | 
			
		||||
    m_keyMap[SDLK_PERCENT] = Fw::KeyPercent;
 | 
			
		||||
    m_keyMap[SDLK_AMPERSAND] = Fw::KeyAmpersand;
 | 
			
		||||
    m_keyMap[SDLK_QUOTE] = Fw::KeyApostrophe;
 | 
			
		||||
    m_keyMap[SDLK_LEFTPAREN] = Fw::KeyLeftParen;
 | 
			
		||||
    m_keyMap[SDLK_RIGHTPAREN] = Fw::KeyRightParen;
 | 
			
		||||
    m_keyMap[SDLK_ASTERISK] = Fw::KeyAsterisk;
 | 
			
		||||
    m_keyMap[SDLK_PLUS] = Fw::KeyPlus;
 | 
			
		||||
    m_keyMap[SDLK_COMMA] = Fw::KeyComma;
 | 
			
		||||
    m_keyMap[SDLK_MINUS] = Fw::KeyMinus;
 | 
			
		||||
    m_keyMap[SDLK_PERIOD] = Fw::KeyPeriod;
 | 
			
		||||
    m_keyMap[SDLK_SLASH] = Fw::KeySlash;
 | 
			
		||||
 | 
			
		||||
    m_keyMap[SDLK_0] = Fw::Key0;
 | 
			
		||||
    m_keyMap[SDLK_1] = Fw::Key1;
 | 
			
		||||
    m_keyMap[SDLK_2] = Fw::Key2;
 | 
			
		||||
    m_keyMap[SDLK_3] = Fw::Key3;
 | 
			
		||||
    m_keyMap[SDLK_4] = Fw::Key4;
 | 
			
		||||
    m_keyMap[SDLK_5] = Fw::Key5;
 | 
			
		||||
    m_keyMap[SDLK_6] = Fw::Key6;
 | 
			
		||||
    m_keyMap[SDLK_7] = Fw::Key7;
 | 
			
		||||
    m_keyMap[SDLK_8] = Fw::Key8;
 | 
			
		||||
    m_keyMap[SDLK_9] = Fw::Key9;
 | 
			
		||||
 | 
			
		||||
    m_keyMap[SDLK_COLON] = Fw::KeyColon;
 | 
			
		||||
    m_keyMap[SDLK_SEMICOLON] = Fw::KeySemicolon;
 | 
			
		||||
    m_keyMap[SDLK_LESS] = Fw::KeyLess;
 | 
			
		||||
    m_keyMap[SDLK_EQUALS] = Fw::KeyEqual;
 | 
			
		||||
    m_keyMap[SDLK_GREATER] = Fw::KeyGreater;
 | 
			
		||||
    m_keyMap[SDLK_QUESTION] = Fw::KeyQuestion;
 | 
			
		||||
    m_keyMap[SDLK_AT] = Fw::KeyAtSign;
 | 
			
		||||
 | 
			
		||||
    m_keyMap[SDLK_a] = Fw::KeyA;
 | 
			
		||||
    m_keyMap[SDLK_b] = Fw::KeyB;
 | 
			
		||||
    m_keyMap[SDLK_c] = Fw::KeyC;
 | 
			
		||||
    m_keyMap[SDLK_d] = Fw::KeyD;
 | 
			
		||||
    m_keyMap[SDLK_e] = Fw::KeyE;
 | 
			
		||||
    m_keyMap[SDLK_f] = Fw::KeyF;
 | 
			
		||||
    m_keyMap[SDLK_g] = Fw::KeyG;
 | 
			
		||||
    m_keyMap[SDLK_h] = Fw::KeyH;
 | 
			
		||||
    m_keyMap[SDLK_i] = Fw::KeyI;
 | 
			
		||||
    m_keyMap[SDLK_j] = Fw::KeyJ;
 | 
			
		||||
    m_keyMap[SDLK_k] = Fw::KeyK;
 | 
			
		||||
    m_keyMap[SDLK_l] = Fw::KeyL;
 | 
			
		||||
    m_keyMap[SDLK_m] = Fw::KeyM;
 | 
			
		||||
    m_keyMap[SDLK_n] = Fw::KeyN;
 | 
			
		||||
    m_keyMap[SDLK_o] = Fw::KeyO;
 | 
			
		||||
    m_keyMap[SDLK_p] = Fw::KeyP;
 | 
			
		||||
    m_keyMap[SDLK_q] = Fw::KeyQ;
 | 
			
		||||
    m_keyMap[SDLK_r] = Fw::KeyR;
 | 
			
		||||
    m_keyMap[SDLK_s] = Fw::KeyS;
 | 
			
		||||
    m_keyMap[SDLK_t] = Fw::KeyT;
 | 
			
		||||
    m_keyMap[SDLK_u] = Fw::KeyU;
 | 
			
		||||
    m_keyMap[SDLK_v] = Fw::KeyV;
 | 
			
		||||
    m_keyMap[SDLK_w] = Fw::KeyW;
 | 
			
		||||
    m_keyMap[SDLK_x] = Fw::KeyX;
 | 
			
		||||
    m_keyMap[SDLK_y] = Fw::KeyY;
 | 
			
		||||
    m_keyMap[SDLK_z] = Fw::KeyZ;
 | 
			
		||||
 | 
			
		||||
    m_keyMap[SDLK_LGUI] = Fw::KeyLeftBracket;
 | 
			
		||||
    m_keyMap[SDLK_BACKSLASH] = Fw::KeyBackslash;
 | 
			
		||||
    m_keyMap[SDLK_RIGHTBRACKET] = Fw::KeyRightBracket;
 | 
			
		||||
    m_keyMap[SDLK_CARET] = Fw::KeyCaret;
 | 
			
		||||
    m_keyMap[SDLK_UNDERSCORE] = Fw::KeyUnderscore;
 | 
			
		||||
    m_keyMap[SDLK_BACKQUOTE] = Fw::KeyGrave;
 | 
			
		||||
 | 
			
		||||
    // keypad
 | 
			
		||||
    /*
 | 
			
		||||
    m_keyMap[SDLK_KP_PLUS] = Fw::KeyPlus;
 | 
			
		||||
    m_keyMap[SDLK_KP_MINUS] = Fw::KeyMinus;
 | 
			
		||||
    m_keyMap[SDLK_KP_DECIMAL] = Fw::KeyPeriod;
 | 
			
		||||
    m_keyMap[SDLK_KP_DIVIDE] = Fw::KeySlash;
 | 
			
		||||
    m_keyMap[SDLK_KP_MULTIPLY] = Fw::KeyAsterisk;
 | 
			
		||||
 | 
			
		||||
    m_keyMap[VK_OEM_1] = Fw::KeySemicolon;
 | 
			
		||||
    m_keyMap[VK_OEM_2] = Fw::KeySlash;
 | 
			
		||||
    m_keyMap[VK_OEM_3] = Fw::KeyGrave;
 | 
			
		||||
    m_keyMap[VK_OEM_4] = Fw::KeyLeftBracket;
 | 
			
		||||
    m_keyMap[VK_OEM_5] = Fw::KeyBackslash;
 | 
			
		||||
    m_keyMap[VK_OEM_6] = Fw::KeyRightBracket;
 | 
			
		||||
    m_keyMap[VK_OEM_7] = Fw::KeyApostrophe;
 | 
			
		||||
    m_keyMap[VK_OEM_MINUS] = Fw::KeyMinus;
 | 
			
		||||
    m_keyMap[VK_OEM_PLUS] = Fw::KeyEqual;
 | 
			
		||||
    m_keyMap[SDLK_KP_COMMA] = Fw::KeyComma;
 | 
			
		||||
    m_keyMap[VK_OEM_PERIOD] = Fw::KeyPeriod;
 | 
			
		||||
 | 
			
		||||
    m_keyMap[SDLK_F1] = Fw::KeyF1;
 | 
			
		||||
    m_keyMap[SDLK_F2] = Fw::KeyF2;
 | 
			
		||||
    m_keyMap[SDLK_F3] = Fw::KeyF3;
 | 
			
		||||
    m_keyMap[SDLK_F4] = Fw::KeyF4;
 | 
			
		||||
    m_keyMap[SDLK_F5] = Fw::KeyF5;
 | 
			
		||||
    m_keyMap[SDLK_F6] = Fw::KeyF6;
 | 
			
		||||
    m_keyMap[SDLK_F7] = Fw::KeyF7;
 | 
			
		||||
    m_keyMap[SDLK_F8] = Fw::KeyF8;
 | 
			
		||||
    m_keyMap[SDLK_F9] = Fw::KeyF9;
 | 
			
		||||
    m_keyMap[SDLK_F10] = Fw::KeyF10;
 | 
			
		||||
    m_keyMap[SDLK_F11] = Fw::KeyF11;
 | 
			
		||||
    m_keyMap[SDLK_F12] = Fw::KeyF12;
 | 
			
		||||
    */
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::init() {
 | 
			
		||||
    initializeSDL();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::initializeSDL() {
 | 
			
		||||
    if(SDL_Init(SDL_INIT_VIDEO) != 0 ) {
 | 
			
		||||
        g_logger.fatal( stdext::format("Unable to initialize SDL: %s", SDL_GetError()) );
 | 
			
		||||
        terminate();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    setSDLAttributes();
 | 
			
		||||
 | 
			
		||||
    SDL_GetDisplayMode(0, 0, &m_mode);
 | 
			
		||||
    int width = m_mode.w;
 | 
			
		||||
    int height = m_mode.h;
 | 
			
		||||
 | 
			
		||||
    m_window = SDL_CreateWindow( NULL, 0, 0, width, height, SDL_WINDOW_OPENGL | SDL_WINDOW_FULLSCREEN | SDL_WINDOW_RESIZABLE );
 | 
			
		||||
 | 
			
		||||
    m_size = Size( width, height );
 | 
			
		||||
 | 
			
		||||
    if( m_window == 0 ) {
 | 
			
		||||
        g_logger.fatal("Failed to create window");
 | 
			
		||||
        terminate();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    m_visible = true;
 | 
			
		||||
 | 
			
		||||
    SDL_GL_CreateContext(m_window);
 | 
			
		||||
    //SDL_StartTextInput();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::setSDLAttributes() {
 | 
			
		||||
    SDL_LogSetAllPriority(SDL_LOG_PRIORITY_VERBOSE);
 | 
			
		||||
 | 
			
		||||
    SDL_GL_SetAttribute(SDL_GL_RED_SIZE, 4);
 | 
			
		||||
    SDL_GL_SetAttribute(SDL_GL_GREEN_SIZE, 4);
 | 
			
		||||
    SDL_GL_SetAttribute(SDL_GL_BLUE_SIZE, 4);
 | 
			
		||||
    SDL_GL_SetAttribute(SDL_GL_ALPHA_SIZE, 4);
 | 
			
		||||
    SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, SDL_GL_CONTEXT_PROFILE_ES);
 | 
			
		||||
    SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, OPENGL_ES);
 | 
			
		||||
    SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, 1);
 | 
			
		||||
    SDL_GL_SetAttribute(SDL_GL_ACCELERATED_VISUAL, 1);
 | 
			
		||||
    SDL_GL_SetAttribute(SDL_GL_DEPTH_SIZE, 0);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::terminate() {
 | 
			
		||||
    SDL_Quit();
 | 
			
		||||
    m_visible = false;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::poll() {
 | 
			
		||||
    while(SDL_PollEvent(&m_event)) {
 | 
			
		||||
        processKeydownOrKeyrelease();
 | 
			
		||||
 | 
			
		||||
        switch(m_event.type) {
 | 
			
		||||
            case SDL_TEXTINPUT:
 | 
			
		||||
                processTextInput();
 | 
			
		||||
                break;
 | 
			
		||||
            case SDL_FINGERDOWN:
 | 
			
		||||
            case SDL_FINGERUP:
 | 
			
		||||
                processFingerdownAndFingerup();
 | 
			
		||||
                break;
 | 
			
		||||
            case SDL_FINGERMOTION:
 | 
			
		||||
				processFingermotion();
 | 
			
		||||
                break;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        //if(m_inputEvent.type != Fw::NoInputEvent && m_onInputEvent)
 | 
			
		||||
        //    m_onInputEvent(m_inputEvent);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    fireKeysPress();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::processKeydownOrKeyrelease() {
 | 
			
		||||
    if(m_event.key.state == SDL_PRESSED || m_event.key.state == SDL_RELEASED) {
 | 
			
		||||
        Fw::Key keyCode = Fw::KeyUnknown;
 | 
			
		||||
        SDL_Keycode keysym = m_event.key.keysym.sym;
 | 
			
		||||
 | 
			
		||||
        if(m_keyMap.find(keysym) != m_keyMap.end())
 | 
			
		||||
            keyCode = m_keyMap[keysym];
 | 
			
		||||
 | 
			
		||||
        if(m_event.type == SDL_PRESSED)
 | 
			
		||||
            processKeyDown(keyCode);
 | 
			
		||||
        else if(m_event.type == SDL_RELEASED)
 | 
			
		||||
            processKeyUp(keyCode);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::processTextInput() {
 | 
			
		||||
    std::string text = m_event.text.text;
 | 
			
		||||
    SDL_Keycode keysym = m_event.key.keysym.sym;
 | 
			
		||||
 | 
			
		||||
    if(text.length() == 0 || keysym == SDLK_BACKSPACE || keysym == SDLK_RETURN || keysym == SDLK_AC_BACK || keysym == SDLK_DELETE)
 | 
			
		||||
        return;
 | 
			
		||||
 | 
			
		||||
    if(m_onInputEvent) {
 | 
			
		||||
        m_inputEvent.reset(Fw::KeyTextInputEvent);
 | 
			
		||||
        m_inputEvent.keyText = text;
 | 
			
		||||
        m_onInputEvent(m_inputEvent);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::processFingerdownAndFingerup() {
 | 
			
		||||
    bool isFinderdown = m_event.type == SDL_FINGERDOWN;
 | 
			
		||||
 | 
			
		||||
    m_inputEvent.reset();
 | 
			
		||||
    m_inputEvent.type = isFinderdown ? Fw::MousePressInputEvent : Fw::MouseReleaseInputEvent;
 | 
			
		||||
    m_inputEvent.mouseButton = Fw::MouseLeftButton;
 | 
			
		||||
    m_mouseButtonStates[Fw::MouseLeftButton] = isFinderdown;
 | 
			
		||||
 | 
			
		||||
    Point newMousePos(m_event.tfinger.x * m_mode.w, m_event.tfinger.y * m_mode.h);
 | 
			
		||||
    m_inputEvent.mouseMoved = newMousePos - m_inputEvent.mousePos;
 | 
			
		||||
    m_inputEvent.mousePos = newMousePos;
 | 
			
		||||
 | 
			
		||||
    if(m_onInputEvent)
 | 
			
		||||
        m_onInputEvent(m_inputEvent);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::processFingermotion() {
 | 
			
		||||
	m_inputEvent.reset();
 | 
			
		||||
	m_inputEvent.type = Fw::MouseMoveInputEvent;
 | 
			
		||||
	Point newMousePos(m_event.tfinger.x * m_mode.w, m_event.tfinger.y * m_mode.h);
 | 
			
		||||
	m_inputEvent.mouseMoved = newMousePos - m_inputEvent.mousePos;
 | 
			
		||||
	m_inputEvent.mousePos = newMousePos;
 | 
			
		||||
	if (m_onInputEvent)
 | 
			
		||||
		m_onInputEvent(m_inputEvent);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::swapBuffers() {
 | 
			
		||||
    SDL_GL_SwapWindow(m_window);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::setVerticalSync(bool enable) {
 | 
			
		||||
	SDL_GL_SetSwapInterval(enable);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
std::string SDLWindow::getClipboardText() {
 | 
			
		||||
    return SDL_GetClipboardText();
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::setClipboardText(const std::string& text) {
 | 
			
		||||
    SDL_SetClipboardText(text.c_str());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
Size SDLWindow::getDisplaySize() {
 | 
			
		||||
    Size size(m_mode.w, m_mode.h);
 | 
			
		||||
    return size;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
std::string SDLWindow::getPlatformType() {
 | 
			
		||||
    return "MOBILE_SDL2";
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::show() {
 | 
			
		||||
    // mobile devices doesn't need to show activity, it's open automatically
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::hide() {
 | 
			
		||||
    // SDL make this for us
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::maximize() {
 | 
			
		||||
    // mobile devices doesn't has window
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::move(const Point& pos) {
 | 
			
		||||
    // mobile devices doesn't has window
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::resize(const Size& size) {
 | 
			
		||||
    // android doesn't resize window
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::showMouse() {
 | 
			
		||||
    // mobile devices doesn't has mouse
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::hideMouse() {
 | 
			
		||||
    // mobile devices doesn't has mouse
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int SDLWindow::internalLoadMouseCursor(const ImagePtr& image, const Point& hotSpot) {
 | 
			
		||||
    // mobile devices doesn't has mouse
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::setMouseCursor(int cursorId) {
 | 
			
		||||
    // mobile devices doesn't has mouse
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::restoreMouseCursor() {
 | 
			
		||||
    // mobile devices doesn't has mouse
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::setTitle(const std::string& title) {
 | 
			
		||||
    // mobile devices doesn't need to set title, the app make it
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::setMinimumSize(const Size& minimumSize) {
 | 
			
		||||
    // mobile devices doesn't has window
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::setFullscreen(bool fullscreen) {
 | 
			
		||||
    // mobile devices doesn't has window
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void SDLWindow::setIcon(const std::string& iconFile) {
 | 
			
		||||
    // mobile devices doesn't has icon
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#endif // ANDROID
 | 
			
		||||
@@ -1,77 +0,0 @@
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2010-2014 OTClient <https://github.com/edubart/otclient>
 | 
			
		||||
 *
 | 
			
		||||
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 | 
			
		||||
 * of this software and associated documentation files (the "Software"), to deal
 | 
			
		||||
 * in the Software without restriction, including without limitation the rights
 | 
			
		||||
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 | 
			
		||||
 * copies of the Software, and to permit persons to whom the Software is
 | 
			
		||||
 * furnished to do so, subject to the following conditions:
 | 
			
		||||
 *
 | 
			
		||||
 * The above copyright notice and this permission notice shall be included in
 | 
			
		||||
 * all copies or substantial portions of the Software.
 | 
			
		||||
 *
 | 
			
		||||
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 | 
			
		||||
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 | 
			
		||||
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 | 
			
		||||
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 | 
			
		||||
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 | 
			
		||||
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 | 
			
		||||
 * THE SOFTWARE.
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#ifndef SDL_PLATFORM_H
 | 
			
		||||
#define SDL_PLATFORM_H
 | 
			
		||||
 | 
			
		||||
#include "platformwindow.h"
 | 
			
		||||
#include <EGL/egl.h>
 | 
			
		||||
#include <SDL.h>
 | 
			
		||||
 | 
			
		||||
class SDLWindow : public PlatformWindow
 | 
			
		||||
{
 | 
			
		||||
public:
 | 
			
		||||
    SDLWindow();
 | 
			
		||||
 | 
			
		||||
    void init();
 | 
			
		||||
    void terminate();
 | 
			
		||||
 | 
			
		||||
    void move(const Point& pos);
 | 
			
		||||
    void resize(const Size& size);
 | 
			
		||||
    void show();
 | 
			
		||||
    void hide();
 | 
			
		||||
    void maximize();
 | 
			
		||||
    void poll();
 | 
			
		||||
    void swapBuffers();
 | 
			
		||||
    void showMouse();
 | 
			
		||||
    void hideMouse();
 | 
			
		||||
 | 
			
		||||
    void setMouseCursor(int cursorId);
 | 
			
		||||
    void restoreMouseCursor();
 | 
			
		||||
 | 
			
		||||
    void setTitle(const std::string& title);
 | 
			
		||||
    void setMinimumSize(const Size& minimumSize);
 | 
			
		||||
    void setFullscreen(bool fullscreen);
 | 
			
		||||
    void setVerticalSync(bool enable);
 | 
			
		||||
    void setIcon(const std::string& iconFile);
 | 
			
		||||
    void setClipboardText(const std::string& text);
 | 
			
		||||
 | 
			
		||||
    Size getDisplaySize();
 | 
			
		||||
    std::string getClipboardText();
 | 
			
		||||
    std::string getPlatformType();
 | 
			
		||||
 | 
			
		||||
    void initializeSDL();
 | 
			
		||||
    void setSDLAttributes();
 | 
			
		||||
    void processKeydownOrKeyrelease();
 | 
			
		||||
    void processTextInput();
 | 
			
		||||
    void processFingerdownAndFingerup();
 | 
			
		||||
	void processFingermotion();
 | 
			
		||||
 | 
			
		||||
protected:
 | 
			
		||||
    int internalLoadMouseCursor(const ImagePtr& image, const Point& hotSpot);
 | 
			
		||||
private:
 | 
			
		||||
    SDL_Window* m_window;
 | 
			
		||||
    SDL_DisplayMode m_mode;
 | 
			
		||||
    SDL_Event m_event;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
#endif
 | 
			
		||||
@@ -206,7 +206,12 @@ std::string Platform::traceback(const std::string& where, int level, int maxDept
 | 
			
		||||
    return ss.str();
 | 
			
		||||
}
 | 
			
		||||
#else
 | 
			
		||||
std::string Platform::traceback(const std::string& where, int level, int maxDepth){ return " ANDROID TRACEBACK NEED TO DO"; }
 | 
			
		||||
std::string Platform::traceback(const std::string& where, int level, int maxDepth){
 | 
			
		||||
	std::stringstream ss;
 | 
			
		||||
    ss << "\nat:";
 | 
			
		||||
    ss << "\n\t[C++]: " << where;
 | 
			
		||||
    return ss.str();
 | 
			
		||||
}
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
#endif
 | 
			
		||||
 
 | 
			
		||||
@@ -659,9 +659,8 @@ void UITextEdit::onFocusChange(bool focused, Fw::FocusReason reason)
 | 
			
		||||
        else
 | 
			
		||||
            blinkCursor();
 | 
			
		||||
        update(true);
 | 
			
		||||
 | 
			
		||||
#ifdef ANDROID
 | 
			
		||||
        SDL_StartTextInput();
 | 
			
		||||
        g_mobileFacade.showKeyboardSoft();
 | 
			
		||||
#endif
 | 
			
		||||
    } else if(m_selectable)
 | 
			
		||||
        clearSelection();
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user