mirror of
https://github.com/love2d/love-android.git
synced 2026-08-12 08:31:04 +02:00
updated to latest love-android revision (aada9b59bcdf)
This commit is contained in:
+3
-1
@@ -3,7 +3,9 @@
|
||||
android:versionCode="7"
|
||||
android:versionName="0.9.0-alpha7"
|
||||
android:installLocation="auto" xmlns:android="http://schemas.android.com/apk/res/android">
|
||||
<uses-permission android:name="android.permission.INTERNET"/><application
|
||||
<uses-permission android:name="android.permission.INTERNET"/>
|
||||
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
|
||||
<application
|
||||
android:allowBackup="true"
|
||||
android:icon="@drawable/ic_launcher"
|
||||
android:label="Löve for Android"
|
||||
|
||||
@@ -43,8 +43,7 @@ LOCAL_SRC_FILES := \
|
||||
$(wildcard $(LOCAL_PATH)/src/timer/*.c) \
|
||||
$(wildcard $(LOCAL_PATH)/src/timer/unix/*.c) \
|
||||
$(wildcard $(LOCAL_PATH)/src/video/*.c) \
|
||||
$(wildcard $(LOCAL_PATH)/src/video/android/*.c) \
|
||||
$(wildcard $(LOCAL_PATH)/src/test/*.c))
|
||||
$(wildcard $(LOCAL_PATH)/src/video/android/*.c))
|
||||
|
||||
LOCAL_CFLAGS += -DGL_GLEXT_PROTOTYPES
|
||||
LOCAL_LDLIBS := -ldl -lGLESv1_CM -lGLESv2 -llog -landroid
|
||||
|
||||
@@ -71,6 +71,8 @@ LOCAL_SRC_FILES := \
|
||||
$(wildcard ${LOCAL_PATH}/src/modules/system/sdl/*.cpp) \
|
||||
$(wildcard ${LOCAL_PATH}/src/modules/thread/*.cpp) \
|
||||
$(wildcard ${LOCAL_PATH}/src/modules/thread/sdl/*.cpp) \
|
||||
$(wildcard ${LOCAL_PATH}/src/modules/touch/*.cpp) \
|
||||
$(wildcard ${LOCAL_PATH}/src/modules/touch/sdl/*.cpp) \
|
||||
$(wildcard ${LOCAL_PATH}/src/modules/timer/*.cpp) \
|
||||
$(wildcard ${LOCAL_PATH}/src/modules/timer/sdl/*.cpp) \
|
||||
$(wildcard ${LOCAL_PATH}/src/modules/window/*.cpp) \
|
||||
|
||||
@@ -26,7 +26,11 @@
|
||||
# define LOVE_WINDOWS 1
|
||||
#endif
|
||||
#if defined(linux) || defined(__linux) || defined(__linux__)
|
||||
# define LOVE_LINUX 1
|
||||
# if defined(__ANDROID__)
|
||||
# define LOVE_ANDROID 1
|
||||
# else
|
||||
# define LOVE_LINUX 1
|
||||
# endif
|
||||
#endif
|
||||
#if defined(__APPLE__)
|
||||
# define LOVE_MACOSX 1
|
||||
@@ -123,6 +127,8 @@
|
||||
# define LOVE_ENABLE_THREAD_SDL
|
||||
# define LOVE_ENABLE_TIMER
|
||||
# define LOVE_ENABLE_TIMER_SDL
|
||||
# define LOVE_ENABLE_TOUCH
|
||||
# define LOVE_ENABLE_TOUCH_SDL
|
||||
# define LOVE_ENABLE_UTF8
|
||||
# define LOVE_ENABLE_WINDOW
|
||||
# define LOVE_ENABLE_WINDOW_SDL
|
||||
|
||||
@@ -464,7 +464,7 @@ void luax_pushtype(lua_State *L, const char *name, bits flags, love::Object *dat
|
||||
|
||||
bool luax_istype(lua_State *L, int idx, love::bits type)
|
||||
{
|
||||
if (lua_isuserdata(L, idx) == 0)
|
||||
if (lua_type(L, idx) != LUA_TUSERDATA)
|
||||
return false;
|
||||
|
||||
return ((((Proxy *)lua_touserdata(L, idx))->flags & type) == type);
|
||||
|
||||
@@ -401,7 +401,7 @@ extern "C" { // Also called from luasocket
|
||||
template <typename T>
|
||||
T *luax_checktype(lua_State *L, int idx, const char *name, love::bits type)
|
||||
{
|
||||
if (lua_isuserdata(L, idx) == 0)
|
||||
if (lua_type(L, idx) != LUA_TUSERDATA)
|
||||
luax_typerror(L, idx, name);
|
||||
|
||||
Proxy *u = (Proxy *)lua_touserdata(L, idx);
|
||||
|
||||
@@ -151,7 +151,7 @@ static const struct luaL_Reg sdl_lib[] = {
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
#ifdef __ANDROID__
|
||||
#ifdef LOVE_ANDROID
|
||||
SDL_SetHint("LOVE_GRAPHICS_USE_OPENGLES", "1");
|
||||
#endif
|
||||
|
||||
@@ -248,7 +248,7 @@ int main(int argc, char **argv)
|
||||
#endif // LOVE_LEGENDARY_UTF8_ARGV_HACK || LOVE_LEGENDARY_APP_ARGV_HACK
|
||||
SDL_Quit();
|
||||
|
||||
#ifdef __ANDROID__
|
||||
#ifdef LOVE_ANDROID
|
||||
exit(retval);
|
||||
#endif
|
||||
|
||||
|
||||
@@ -28,56 +28,70 @@ namespace love
|
||||
namespace event
|
||||
{
|
||||
|
||||
Message::Message(const std::string &name, Variant *a, Variant *b, Variant *c, Variant *d)
|
||||
Message::Message(const std::string &name, const std::vector<Variant *> &vargs)
|
||||
: name(name)
|
||||
, nargs(0)
|
||||
, args(vargs)
|
||||
{
|
||||
args[0] = a;
|
||||
args[1] = b;
|
||||
args[2] = c;
|
||||
args[3] = d;
|
||||
for (int i = 0; i < 4; i++)
|
||||
for (auto it = args.begin(); it != args.end(); ++it)
|
||||
{
|
||||
if (!args[i])
|
||||
break;
|
||||
args[i]->retain();
|
||||
nargs++;
|
||||
if ((*it) != nullptr)
|
||||
(*it)->retain();
|
||||
}
|
||||
}
|
||||
|
||||
Message::~Message()
|
||||
{
|
||||
for (int i = 0; i < nargs; i++)
|
||||
args[i]->release();
|
||||
for (auto it = args.begin(); it != args.end(); ++it)
|
||||
{
|
||||
if ((*it) != nullptr)
|
||||
(*it)->release();
|
||||
}
|
||||
}
|
||||
|
||||
int Message::toLua(lua_State *L)
|
||||
{
|
||||
luax_pushstring(L, name);
|
||||
for (int i = 0; i < nargs; i++)
|
||||
args[i]->toLua(L);
|
||||
return nargs+1;
|
||||
|
||||
for (auto it = args.begin(); it != args.end(); ++it)
|
||||
{
|
||||
if ((*it) != nullptr)
|
||||
(*it)->toLua(L);
|
||||
else
|
||||
lua_pushnil(L);
|
||||
}
|
||||
|
||||
return (int) args.size() + 1;
|
||||
}
|
||||
|
||||
Message *Message::fromLua(lua_State *L, int n)
|
||||
{
|
||||
std::string name = luax_checkstring(L, n);
|
||||
std::vector<Variant *> vargs;
|
||||
|
||||
int count = lua_gettop(L) - n;
|
||||
n++;
|
||||
Message *m = new Message(name);
|
||||
for (int i = 0; i < 4; i++)
|
||||
|
||||
for (int i = 0; i < count; i++)
|
||||
{
|
||||
if (lua_isnoneornil(L, n+i))
|
||||
break;
|
||||
m->args[i] = Variant::fromLua(L, n+i);
|
||||
if (!m->args[i])
|
||||
|
||||
vargs.push_back(Variant::fromLua(L, n+i));
|
||||
|
||||
if (!vargs.back())
|
||||
{
|
||||
delete m;
|
||||
for (auto it = vargs.begin(); it != vargs.end(); ++it)
|
||||
{
|
||||
if ((*it) != nullptr)
|
||||
(*it)->release();
|
||||
}
|
||||
|
||||
luaL_error(L, "Argument %d can't be stored safely\nExpected boolean, number, string or userdata.", n+i);
|
||||
return NULL;
|
||||
return nullptr;
|
||||
}
|
||||
m->nargs++;
|
||||
}
|
||||
return m;
|
||||
|
||||
return new Message(name, vargs);
|
||||
}
|
||||
|
||||
Event::Event()
|
||||
|
||||
@@ -32,29 +32,34 @@
|
||||
|
||||
// STL
|
||||
#include <queue>
|
||||
#include <vector>
|
||||
|
||||
namespace love
|
||||
{
|
||||
namespace event
|
||||
{
|
||||
|
||||
class Message : public Object
|
||||
{
|
||||
private:
|
||||
std::string name;
|
||||
Variant *args[4];
|
||||
int nargs;
|
||||
|
||||
public:
|
||||
Message(const std::string &name, Variant *a = NULL, Variant *b = NULL, Variant *c = NULL, Variant *d = NULL);
|
||||
|
||||
Message(const std::string &name, const std::vector<Variant *> &vargs = std::vector<Variant *>());
|
||||
~Message();
|
||||
|
||||
int toLua(lua_State *L);
|
||||
static Message *fromLua(lua_State *L, int n);
|
||||
};
|
||||
|
||||
private:
|
||||
|
||||
std::string name;
|
||||
std::vector<Variant *> args;
|
||||
|
||||
}; // Message
|
||||
|
||||
class Event : public Module
|
||||
{
|
||||
public:
|
||||
|
||||
Event();
|
||||
virtual ~Event();
|
||||
|
||||
@@ -65,6 +70,7 @@ public:
|
||||
virtual void pump() = 0;
|
||||
|
||||
protected:
|
||||
|
||||
thread::Mutex *mutex;
|
||||
std::queue<Message *> queue;
|
||||
|
||||
|
||||
@@ -38,6 +38,24 @@ namespace event
|
||||
namespace sdl
|
||||
{
|
||||
|
||||
// SDL reports mouse coordinates in the window coordinate system in OS X, but
|
||||
// we want them in pixel coordinates (may be different with high-DPI enabled.)
|
||||
static void windowToPixelCoords(int *x, int *y)
|
||||
{
|
||||
double scale = 1.0;
|
||||
|
||||
window::Window *window = (window::Window *) Module::findInstance("love.window.");
|
||||
if (window != nullptr)
|
||||
scale = window->getPixelScale();
|
||||
|
||||
if (x != nullptr)
|
||||
*x = int(double(*x) * scale);
|
||||
|
||||
if (y != nullptr)
|
||||
*y = int(double(*y) * scale);
|
||||
}
|
||||
|
||||
|
||||
const char *Event::getName() const
|
||||
{
|
||||
return "love.event.sdl";
|
||||
@@ -96,19 +114,22 @@ void Event::clear()
|
||||
|
||||
Message *Event::convert(const SDL_Event &e) const
|
||||
{
|
||||
Message *msg = NULL;
|
||||
Message *msg = nullptr;
|
||||
|
||||
love::keyboard::Keyboard *kb = 0;
|
||||
std::vector<Variant *> vargs;
|
||||
vargs.reserve(4);
|
||||
|
||||
love::keyboard::Keyboard *kb = nullptr;
|
||||
|
||||
love::keyboard::Keyboard::Key key;
|
||||
love::mouse::Mouse::Button button;
|
||||
Variant *arg1, *arg2, *arg3;
|
||||
const char *txt;
|
||||
std::map<SDL_Keycode, love::keyboard::Keyboard::Key>::const_iterator keyit;
|
||||
|
||||
switch (e.type)
|
||||
{
|
||||
case SDL_KEYDOWN:
|
||||
SDL_Log ("got keydown for key %d search %d equal = %d", e.key.keysym.sym, SDLK_AC_SEARCH, e.key.keysym.sym == SDLK_AC_SEARCH);
|
||||
if (e.key.repeat)
|
||||
{
|
||||
kb = (love::keyboard::Keyboard *) Module::findInstance("love.keyboard.");
|
||||
@@ -124,11 +145,10 @@ Message *Event::convert(const SDL_Event &e) const
|
||||
|
||||
if (!love::keyboard::Keyboard::getConstant(key, txt))
|
||||
txt = "unknown";
|
||||
arg1 = new Variant(txt, strlen(txt));
|
||||
arg2 = new Variant(e.key.repeat != 0);
|
||||
msg = new Message("keypressed", arg1, arg2);
|
||||
arg1->release();
|
||||
arg2->release();
|
||||
|
||||
vargs.push_back(new Variant(txt, strlen(txt)));
|
||||
vargs.push_back(new Variant(e.key.repeat != 0));
|
||||
msg = new Message("keypressed", vargs);
|
||||
break;
|
||||
case SDL_KEYUP:
|
||||
keyit = keys.find(e.key.keysym.sym);
|
||||
@@ -139,39 +159,36 @@ Message *Event::convert(const SDL_Event &e) const
|
||||
|
||||
if (!love::keyboard::Keyboard::getConstant(key, txt))
|
||||
txt = "unknown";
|
||||
arg1 = new Variant(txt, strlen(txt));
|
||||
msg = new Message("keyreleased", arg1);
|
||||
arg1->release();
|
||||
|
||||
vargs.push_back(new Variant(txt, strlen(txt)));
|
||||
msg = new Message("keyreleased", vargs);
|
||||
break;
|
||||
case SDL_TEXTINPUT:
|
||||
txt = e.text.text;
|
||||
arg1 = new Variant(txt, strlen(txt));
|
||||
msg = new Message("textinput", arg1);
|
||||
arg1->release();
|
||||
vargs.push_back(new Variant(txt, strlen(txt)));
|
||||
msg = new Message("textinput", vargs);
|
||||
break;
|
||||
case SDL_TEXTEDITING:
|
||||
txt = e.edit.text;
|
||||
arg1 = new Variant(txt, strlen(txt));
|
||||
arg2 = new Variant((double) e.edit.start);
|
||||
arg3 = new Variant((double) e.edit.length);
|
||||
msg = new Message("textedit", arg1, arg2, arg3);
|
||||
arg1->release();
|
||||
arg2->release();
|
||||
arg3->release();
|
||||
vargs.push_back(new Variant(txt, strlen(txt)));
|
||||
vargs.push_back(new Variant((double) e.edit.start));
|
||||
vargs.push_back(new Variant((double) e.edit.length));
|
||||
msg = new Message("textedit", vargs);
|
||||
break;
|
||||
case SDL_MOUSEBUTTONDOWN:
|
||||
case SDL_MOUSEBUTTONUP:
|
||||
if (buttons.find(e.button.button, button) && mouse::Mouse::getConstant(button, txt))
|
||||
{
|
||||
arg1 = new Variant((double) e.button.x);
|
||||
arg2 = new Variant((double) e.button.y);
|
||||
arg3 = new Variant(txt, strlen(txt));
|
||||
int x = e.button.x;
|
||||
int y = e.button.y;
|
||||
windowToPixelCoords(&x, &y);
|
||||
vargs.push_back(new Variant((double) x));
|
||||
vargs.push_back(new Variant((double) y));
|
||||
vargs.push_back(new Variant(txt, strlen(txt)));
|
||||
vargs.push_back(new Variant(e.button.which == SDL_TOUCH_MOUSEID));
|
||||
msg = new Message((e.type == SDL_MOUSEBUTTONDOWN) ?
|
||||
"mousepressed" : "mousereleased",
|
||||
arg1, arg2, arg3);
|
||||
arg1->release();
|
||||
arg2->release();
|
||||
arg3->release();
|
||||
vargs);
|
||||
}
|
||||
break;
|
||||
case SDL_MOUSEWHEEL:
|
||||
@@ -183,36 +200,29 @@ Message *Event::convert(const SDL_Event &e) const
|
||||
|
||||
int mx, my;
|
||||
SDL_GetMouseState(&mx, &my);
|
||||
windowToPixelCoords(&mx, &my);
|
||||
|
||||
arg1 = new Variant((double) mx);
|
||||
arg2 = new Variant((double) my);
|
||||
arg3 = new Variant(txt, strlen(txt));
|
||||
msg = new Message("mousepressed", arg1, arg2, arg3);
|
||||
arg1->release();
|
||||
arg2->release();
|
||||
arg3->release();
|
||||
vargs.push_back(new Variant((double) mx));
|
||||
vargs.push_back(new Variant((double) my));
|
||||
vargs.push_back(new Variant(txt, strlen(txt)));
|
||||
vargs.push_back(new Variant(false));
|
||||
msg = new Message("mousepressed", vargs);
|
||||
}
|
||||
break;
|
||||
case SDL_FINGERDOWN:
|
||||
case SDL_FINGERUP:
|
||||
arg1 = new Variant((double) e.tfinger.x);
|
||||
arg2 = new Variant((double) e.tfinger.y);
|
||||
arg3 = new Variant((double) e.tfinger.fingerId);
|
||||
msg = new Message((e.type == SDL_FINGERDOWN) ?
|
||||
"fingerpressed" : "fingerreleased",
|
||||
arg1, arg2, arg3);
|
||||
arg1->release();
|
||||
arg2->release();
|
||||
arg3->release();
|
||||
break;
|
||||
case SDL_FINGERMOTION:
|
||||
arg1 = new Variant((double) e.tfinger.x);
|
||||
arg2 = new Variant((double) e.tfinger.y);
|
||||
arg3 = new Variant((double) e.tfinger.fingerId);
|
||||
msg = new Message("fingermotion", arg1, arg2, arg3);
|
||||
arg1->release();
|
||||
arg2->release();
|
||||
arg3->release();
|
||||
vargs.push_back(new Variant((double) e.tfinger.fingerId));
|
||||
vargs.push_back(new Variant((double) e.tfinger.x));
|
||||
vargs.push_back(new Variant((double) e.tfinger.y));
|
||||
vargs.push_back(new Variant((double) e.tfinger.pressure));
|
||||
if (e.type == SDL_FINGERDOWN)
|
||||
txt = "touchpressed";
|
||||
else if (e.type == SDL_FINGERUP)
|
||||
txt = "touchreleased";
|
||||
else
|
||||
txt = "touchmoved";
|
||||
msg = new Message(txt, vargs);
|
||||
break;
|
||||
case SDL_JOYBUTTONDOWN:
|
||||
case SDL_JOYBUTTONUP:
|
||||
@@ -239,6 +249,12 @@ Message *Event::convert(const SDL_Event &e) const
|
||||
break;
|
||||
}
|
||||
|
||||
for (auto it = vargs.begin(); it != vargs.end(); ++it)
|
||||
{
|
||||
if ((*it) != nullptr)
|
||||
(*it)->release();
|
||||
}
|
||||
|
||||
return msg;
|
||||
}
|
||||
|
||||
@@ -246,14 +262,17 @@ Message *Event::convertJoystickEvent(const SDL_Event &e) const
|
||||
{
|
||||
joystick::JoystickModule *joymodule = (joystick::JoystickModule *) Module::findInstance("love.joystick.");
|
||||
if (!joymodule)
|
||||
return 0;
|
||||
return nullptr;
|
||||
|
||||
Message *msg = nullptr;
|
||||
|
||||
std::vector<Variant *> vargs;
|
||||
vargs.reserve(4);
|
||||
|
||||
Message *msg = 0;
|
||||
Proxy proxy;
|
||||
love::joystick::Joystick::Hat hat;
|
||||
love::joystick::Joystick::GamepadButton padbutton;
|
||||
love::joystick::Joystick::GamepadAxis padaxis;
|
||||
Variant *arg1, *arg2, *arg3;
|
||||
const char *txt;
|
||||
|
||||
switch (e.type)
|
||||
@@ -265,13 +284,11 @@ Message *Event::convertJoystickEvent(const SDL_Event &e) const
|
||||
if (!proxy.data)
|
||||
break;
|
||||
|
||||
arg1 = new Variant(JOYSTICK_JOYSTICK_ID, (void *) &proxy);
|
||||
arg2 = new Variant((double)(e.jbutton.button+1));
|
||||
vargs.push_back(new Variant(JOYSTICK_JOYSTICK_ID, (void *) &proxy));
|
||||
vargs.push_back(new Variant((double)(e.jbutton.button+1)));
|
||||
msg = new Message((e.type == SDL_JOYBUTTONDOWN) ?
|
||||
"joystickpressed" : "joystickreleased",
|
||||
arg1, arg2);
|
||||
arg1->release();
|
||||
arg2->release();
|
||||
vargs);
|
||||
break;
|
||||
case SDL_JOYAXISMOTION:
|
||||
{
|
||||
@@ -280,17 +297,14 @@ Message *Event::convertJoystickEvent(const SDL_Event &e) const
|
||||
if (!proxy.data)
|
||||
break;
|
||||
|
||||
arg1 = new Variant(JOYSTICK_JOYSTICK_ID, (void *) &proxy);
|
||||
arg2 = new Variant((double)(e.jaxis.axis+1));
|
||||
vargs.push_back(new Variant(JOYSTICK_JOYSTICK_ID, (void *) &proxy));
|
||||
vargs.push_back(new Variant((double)(e.jaxis.axis+1)));
|
||||
float value = e.jaxis.value / 32768.0f;
|
||||
if (fabsf(value) < 0.001f) value = 0.0f;
|
||||
if (value < -0.99f) value = -1.0f;
|
||||
if (value > 0.99f) value = 1.0f;
|
||||
arg3 = new Variant((double) value);
|
||||
msg = new Message("joystickaxis", arg1, arg2, arg3);
|
||||
arg1->release();
|
||||
arg2->release();
|
||||
arg3->release();
|
||||
vargs.push_back(new Variant((double) value));
|
||||
msg = new Message("joystickaxis", vargs);
|
||||
}
|
||||
break;
|
||||
case SDL_JOYHATMOTION:
|
||||
@@ -302,13 +316,10 @@ Message *Event::convertJoystickEvent(const SDL_Event &e) const
|
||||
if (!proxy.data)
|
||||
break;
|
||||
|
||||
arg1 = new Variant(JOYSTICK_JOYSTICK_ID, (void *) &proxy);
|
||||
arg2 = new Variant((double)(e.jhat.hat+1));
|
||||
arg3 = new Variant(txt, strlen(txt));
|
||||
msg = new Message("joystickhat", arg1, arg2, arg3);
|
||||
arg1->release();
|
||||
arg2->release();
|
||||
arg3->release();
|
||||
vargs.push_back(new Variant(JOYSTICK_JOYSTICK_ID, (void *) &proxy));
|
||||
vargs.push_back(new Variant((double)(e.jhat.hat+1)));
|
||||
vargs.push_back(new Variant(txt, strlen(txt)));
|
||||
msg = new Message("joystickhat", vargs);
|
||||
break;
|
||||
case SDL_CONTROLLERBUTTONDOWN:
|
||||
case SDL_CONTROLLERBUTTONUP:
|
||||
@@ -323,12 +334,10 @@ Message *Event::convertJoystickEvent(const SDL_Event &e) const
|
||||
if (!proxy.data)
|
||||
break;
|
||||
|
||||
arg1 = new Variant(JOYSTICK_JOYSTICK_ID, (void *) &proxy);
|
||||
arg2 = new Variant(txt, strlen(txt));
|
||||
vargs.push_back(new Variant(JOYSTICK_JOYSTICK_ID, (void *) &proxy));
|
||||
vargs.push_back(new Variant(txt, strlen(txt)));
|
||||
msg = new Message(e.type == SDL_CONTROLLERBUTTONDOWN ?
|
||||
"gamepadpressed" : "gamepadreleased", arg1, arg2);
|
||||
arg1->release();
|
||||
arg2->release();
|
||||
"gamepadpressed" : "gamepadreleased", vargs);
|
||||
break;
|
||||
case SDL_CONTROLLERAXISMOTION:
|
||||
if (joystick::sdl::Joystick::getConstant((SDL_GameControllerAxis) e.caxis.axis, padaxis))
|
||||
@@ -341,18 +350,15 @@ Message *Event::convertJoystickEvent(const SDL_Event &e) const
|
||||
if (!proxy.data)
|
||||
break;
|
||||
|
||||
arg1 = new Variant(JOYSTICK_JOYSTICK_ID, (void *) &proxy);
|
||||
vargs.push_back(new Variant(JOYSTICK_JOYSTICK_ID, (void *) &proxy));
|
||||
|
||||
arg2 = new Variant(txt, strlen(txt));
|
||||
vargs.push_back(new Variant(txt, strlen(txt)));
|
||||
float value = e.jaxis.value / 32768.0f;
|
||||
if (fabsf(value) < 0.001f) value = 0.0f;
|
||||
if (value < -0.99f) value = -1.0f;
|
||||
if (value > 0.99f) value = 1.0f;
|
||||
arg3 = new Variant((double) value);
|
||||
msg = new Message("gamepadaxis", arg1, arg2, arg3);
|
||||
arg1->release();
|
||||
arg2->release();
|
||||
arg3->release();
|
||||
vargs.push_back(new Variant((double) value));
|
||||
msg = new Message("gamepadaxis", vargs);
|
||||
}
|
||||
break;
|
||||
case SDL_JOYDEVICEADDED:
|
||||
@@ -361,9 +367,8 @@ Message *Event::convertJoystickEvent(const SDL_Event &e) const
|
||||
proxy.flags = JOYSTICK_JOYSTICK_T;
|
||||
if (proxy.data)
|
||||
{
|
||||
arg1 = new Variant(JOYSTICK_JOYSTICK_ID, (void *) &proxy);
|
||||
msg = new Message("joystickadded", arg1);
|
||||
arg1->release();
|
||||
vargs.push_back(new Variant(JOYSTICK_JOYSTICK_ID, (void *) &proxy));
|
||||
msg = new Message("joystickadded", vargs);
|
||||
}
|
||||
break;
|
||||
case SDL_JOYDEVICEREMOVED:
|
||||
@@ -373,26 +378,34 @@ Message *Event::convertJoystickEvent(const SDL_Event &e) const
|
||||
if (proxy.data)
|
||||
{
|
||||
joymodule->removeJoystick((joystick::Joystick *) proxy.data);
|
||||
arg1 = new Variant(JOYSTICK_JOYSTICK_ID, (void *) &proxy);
|
||||
msg = new Message("joystickremoved", arg1);
|
||||
arg1->release();
|
||||
vargs.push_back(new Variant(JOYSTICK_JOYSTICK_ID, (void *) &proxy));
|
||||
msg = new Message("joystickremoved", vargs);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
for (auto it = vargs.begin(); it != vargs.end(); ++it)
|
||||
{
|
||||
if ((*it) != nullptr)
|
||||
(*it)->release();
|
||||
}
|
||||
|
||||
return msg;
|
||||
}
|
||||
|
||||
Message *Event::convertWindowEvent(const SDL_Event &e) const
|
||||
{
|
||||
Message *msg = 0;
|
||||
Variant *arg1, *arg2;
|
||||
window::Window *win = 0;
|
||||
Message *msg = nullptr;
|
||||
|
||||
std::vector<Variant *> vargs;
|
||||
vargs.reserve(4);
|
||||
|
||||
window::Window *win = nullptr;
|
||||
|
||||
if (e.type != SDL_WINDOWEVENT)
|
||||
return 0;
|
||||
return nullptr;
|
||||
|
||||
switch (e.window.event)
|
||||
{
|
||||
@@ -404,56 +417,69 @@ Message *Event::convertWindowEvent(const SDL_Event &e) const
|
||||
SDL_DisableScreenSaver();
|
||||
else
|
||||
SDL_EnableScreenSaver();
|
||||
arg1 = new Variant(e.window.event == SDL_WINDOWEVENT_FOCUS_GAINED);
|
||||
msg = new Message("focus", arg1);
|
||||
arg1->release();
|
||||
vargs.push_back(new Variant(e.window.event == SDL_WINDOWEVENT_FOCUS_GAINED));
|
||||
msg = new Message("focus", vargs);
|
||||
break;
|
||||
case SDL_WINDOWEVENT_ENTER:
|
||||
case SDL_WINDOWEVENT_LEAVE:
|
||||
arg1 = new Variant(e.window.event == SDL_WINDOWEVENT_ENTER);
|
||||
msg = new Message("mousefocus", arg1);
|
||||
arg1->release();
|
||||
vargs.push_back(new Variant(e.window.event == SDL_WINDOWEVENT_ENTER));
|
||||
msg = new Message("mousefocus", vargs);
|
||||
break;
|
||||
case SDL_WINDOWEVENT_SHOWN:
|
||||
case SDL_WINDOWEVENT_HIDDEN:
|
||||
arg1 = new Variant(e.window.event == SDL_WINDOWEVENT_SHOWN);
|
||||
msg = new Message("visible", arg1);
|
||||
arg1->release();
|
||||
vargs.push_back(new Variant(e.window.event == SDL_WINDOWEVENT_SHOWN));
|
||||
msg = new Message("visible", vargs);
|
||||
break;
|
||||
case SDL_WINDOWEVENT_RESIZED:
|
||||
win = (window::Window *) Module::findInstance("love.window.");
|
||||
if (win)
|
||||
{
|
||||
int px_w = e.window.data1;
|
||||
int px_h = e.window.data2;
|
||||
|
||||
#if SDL_VERSION_ATLEAST(2,0,1)
|
||||
SDL_Window *sdlwin = SDL_GetWindowFromID(e.window.windowID);
|
||||
if (sdlwin)
|
||||
SDL_GL_GetDrawableSize(sdlwin, &px_w, &px_h);
|
||||
#endif
|
||||
|
||||
win->onWindowResize(e.window.data1, e.window.data2);
|
||||
|
||||
graphics::Graphics *gfx = (graphics::Graphics *) Module::findInstance("love.graphics.");
|
||||
if (gfx)
|
||||
gfx->setViewportSize(e.window.data1, e.window.data2);
|
||||
gfx->setViewportSize(px_w, px_h);
|
||||
|
||||
vargs.push_back(new Variant((double) px_w));
|
||||
vargs.push_back(new Variant((double) px_h));
|
||||
vargs.push_back(new Variant((double) e.window.data1));
|
||||
vargs.push_back(new Variant((double) e.window.data2));
|
||||
msg = new Message("resize", vargs);
|
||||
}
|
||||
break;
|
||||
#ifdef LOVE_ANDROID
|
||||
case SDL_WINDOWEVENT_MINIMIZED:
|
||||
{
|
||||
audio::Audio *audio = (audio::Audio *) Module::findInstance("love.audio.");
|
||||
if (audio)
|
||||
audio->pause();
|
||||
}
|
||||
break;
|
||||
case SDL_WINDOWEVENT_RESTORED:
|
||||
{
|
||||
audio::Audio *audio = (audio::Audio *) Module::findInstance("love.audio.");
|
||||
if (audio)
|
||||
audio->resume();
|
||||
}
|
||||
arg1 = new Variant((double) e.window.data1);
|
||||
arg2 = new Variant((double) e.window.data2);
|
||||
msg = new Message("resize", arg1, arg2);
|
||||
arg1->release();
|
||||
arg2->release();
|
||||
break;
|
||||
#ifdef __ANDROID__
|
||||
case SDL_WINDOWEVENT_MINIMIZED:
|
||||
{
|
||||
audio::Audio *audio = (audio::Audio *) Module::findInstance("love.audio.");
|
||||
if (audio)
|
||||
audio->pause();
|
||||
}
|
||||
break;
|
||||
case SDL_WINDOWEVENT_RESTORED:
|
||||
{
|
||||
audio::Audio *audio = (audio::Audio *) Module::findInstance("love.audio.");
|
||||
if (audio)
|
||||
audio->resume();
|
||||
}
|
||||
break;
|
||||
#endif
|
||||
}
|
||||
|
||||
for (auto it = vargs.begin(); it != vargs.end(); ++it)
|
||||
{
|
||||
if ((*it) != nullptr)
|
||||
(*it)->release();
|
||||
}
|
||||
|
||||
return msg;
|
||||
}
|
||||
|
||||
@@ -601,6 +627,7 @@ std::map<SDL_Keycode, love::keyboard::Keyboard::Key> Event::createKeyMap()
|
||||
k[SDLK_EXECUTE] = Keyboard::KEY_EXECUTE;
|
||||
k[SDLK_HELP] = Keyboard::KEY_HELP;
|
||||
k[SDLK_MENU] = Keyboard::KEY_MENU;
|
||||
k[SDLK_AC_SEARCH] = Keyboard::KEY_SEARCH;
|
||||
k[SDLK_SELECT] = Keyboard::KEY_SELECT;
|
||||
k[SDLK_STOP] = Keyboard::KEY_STOP;
|
||||
k[SDLK_AGAIN] = Keyboard::KEY_AGAIN;
|
||||
@@ -656,7 +683,7 @@ std::map<SDL_Keycode, love::keyboard::Keyboard::Key> Event::createKeyMap()
|
||||
k[SDLK_EJECT] = Keyboard::KEY_EJECT;
|
||||
k[SDLK_SLEEP] = Keyboard::KEY_SLEEP;
|
||||
|
||||
#ifdef __ANDROID__
|
||||
#ifdef LOVE_ANDROID
|
||||
k[SDLK_AC_BACK] = Keyboard::KEY_ESCAPE;
|
||||
#endif
|
||||
|
||||
|
||||
@@ -33,11 +33,11 @@ namespace event
|
||||
namespace sdl
|
||||
{
|
||||
|
||||
static Event *instance = 0;
|
||||
static Event *instance = nullptr;
|
||||
|
||||
static int poll_i(lua_State *L)
|
||||
{
|
||||
Message *m;
|
||||
Message *m = nullptr;
|
||||
|
||||
while (instance->poll(m))
|
||||
{
|
||||
@@ -58,13 +58,13 @@ int w_pump(lua_State *)
|
||||
|
||||
int w_poll(lua_State *L)
|
||||
{
|
||||
lua_pushcclosure(L, &poll_i, 0);
|
||||
lua_pushcclosure(L, poll_i, 0);
|
||||
return 1;
|
||||
}
|
||||
|
||||
int w_wait(lua_State *L)
|
||||
{
|
||||
Message *m;
|
||||
Message *m = nullptr;
|
||||
|
||||
if ((m = instance->wait()))
|
||||
{
|
||||
@@ -78,7 +78,7 @@ int w_wait(lua_State *L)
|
||||
|
||||
int w_push(lua_State *L)
|
||||
{
|
||||
Message *m;
|
||||
Message *m = nullptr;
|
||||
|
||||
bool success = (m = Message::fromLua(L, 1)) != NULL;
|
||||
luax_pushboolean(L, success);
|
||||
@@ -133,7 +133,7 @@ extern "C" int luaopen_love_event(lua_State *L)
|
||||
w.name = "event";
|
||||
w.flags = MODULE_T;
|
||||
w.functions = functions;
|
||||
w.types = 0;
|
||||
w.types = nullptr;
|
||||
|
||||
return luax_register_module(L, w);
|
||||
}
|
||||
|
||||
@@ -30,7 +30,7 @@
|
||||
#include "SDL.h"
|
||||
#include <string>
|
||||
|
||||
#ifdef __ANDROID__
|
||||
#ifdef LOVE_ANDROID
|
||||
#include <sys/stat.h>
|
||||
#include <sys/types.h>
|
||||
#include <unistd.h>
|
||||
@@ -58,7 +58,7 @@ namespace
|
||||
return input.substr(getDriveDelim(input)+1);
|
||||
}
|
||||
|
||||
#ifdef __ANDROID__
|
||||
#ifdef LOVE_ANDROID
|
||||
bool androidDirectoryExists(const char* path) {
|
||||
SDL_Log ("Checking directory exists for %s", path);
|
||||
struct stat s;
|
||||
@@ -239,7 +239,7 @@ bool Filesystem::setIdentity(const char *ident, bool appendToPath)
|
||||
else
|
||||
save_path_full += save_path_relative;
|
||||
|
||||
#ifdef __ANDROID__
|
||||
#ifdef LOVE_ANDROID
|
||||
std::string internal_storage_path = SDL_AndroidGetInternalStoragePath();
|
||||
|
||||
std::string save_directory = internal_storage_path + "/save";
|
||||
@@ -297,7 +297,7 @@ bool Filesystem::setSource(const char *source)
|
||||
|
||||
std::string new_search_path = source;
|
||||
|
||||
#ifdef __ANDROID__
|
||||
#ifdef LOVE_ANDROID
|
||||
if (!androidCreateStorageDirectories ()) {
|
||||
SDL_Log ("Error creating storage directories!");
|
||||
}
|
||||
|
||||
@@ -46,7 +46,6 @@ struct GlyphMetrics
|
||||
int advance;
|
||||
int bearingX;
|
||||
int bearingY;
|
||||
int spacing;
|
||||
};
|
||||
|
||||
/**
|
||||
|
||||
@@ -42,14 +42,11 @@ struct FramebufferStrategy
|
||||
|
||||
/// create a new framebuffer and texture
|
||||
/**
|
||||
* @param[out] framebuffer Framebuffer name
|
||||
* @param[out] img Texture name
|
||||
* @param[in] width Width of framebuffer
|
||||
* @param[in] height Height of framebuffer
|
||||
* @param[in] texture_type Type of the canvas texture.
|
||||
* @param[out] framebuffer Framebuffer name
|
||||
* @param[in] texture Texture name
|
||||
* @return Creation status
|
||||
*/
|
||||
virtual GLenum createFBO(GLuint &, GLuint &, int, int, Canvas::TextureType)
|
||||
virtual GLenum createFBO(GLuint &, GLuint)
|
||||
{
|
||||
return GL_FRAMEBUFFER_UNSUPPORTED;
|
||||
}
|
||||
@@ -70,9 +67,8 @@ struct FramebufferStrategy
|
||||
/**
|
||||
* @param[in] framebuffer Framebuffer name
|
||||
* @param[in] depth_stencil Name for packed depth and stencil buffer
|
||||
* @param[in] img Texture name
|
||||
*/
|
||||
virtual void deleteFBO(GLuint, GLuint, GLuint) {}
|
||||
virtual void deleteFBO(GLuint, GLuint) {}
|
||||
virtual void bindFBO(GLuint) {}
|
||||
|
||||
/// attach additional canvases to the active framebuffer for rendering
|
||||
@@ -87,7 +83,7 @@ struct FramebufferStrategy
|
||||
|
||||
struct FramebufferStrategyCore : public FramebufferStrategy
|
||||
{
|
||||
virtual GLenum createFBO(GLuint &framebuffer, GLuint &img, int width, int height, Canvas::TextureType texture_type)
|
||||
virtual GLenum createFBO(GLuint &framebuffer, GLuint texture)
|
||||
{
|
||||
// get currently bound fbo to reset to it later
|
||||
GLint current_fbo;
|
||||
@@ -97,32 +93,8 @@ struct FramebufferStrategyCore : public FramebufferStrategy
|
||||
glGenFramebuffers(1, &framebuffer);
|
||||
glBindFramebuffer(GL_FRAMEBUFFER, framebuffer);
|
||||
|
||||
// generate texture save target
|
||||
GLint internalFormat;
|
||||
GLenum format;
|
||||
switch (texture_type)
|
||||
{
|
||||
case Canvas::TYPE_HDR:
|
||||
internalFormat = GL_RGBA16F;
|
||||
format = GL_FLOAT;
|
||||
break;
|
||||
case Canvas::TYPE_NORMAL:
|
||||
default:
|
||||
internalFormat = GL_RGBA;
|
||||
format = GL_UNSIGNED_BYTE;
|
||||
}
|
||||
|
||||
glGenTextures(1, &img);
|
||||
gl.bindTexture(img);
|
||||
|
||||
Texture::Filter filter = Texture::getDefaultFilter();
|
||||
gl.setTextureFilter(filter);
|
||||
|
||||
glTexImage2D(GL_TEXTURE_2D, 0, internalFormat, width, height,
|
||||
0, GL_RGBA, format, NULL);
|
||||
gl.bindTexture(0);
|
||||
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0,
|
||||
GL_TEXTURE_2D, img, 0);
|
||||
GL_TEXTURE_2D, texture, 0);
|
||||
|
||||
// check status
|
||||
GLenum status = glCheckFramebufferStatus(GL_FRAMEBUFFER);
|
||||
@@ -149,9 +121,8 @@ struct FramebufferStrategyCore : public FramebufferStrategy
|
||||
return glCheckFramebufferStatus(GL_FRAMEBUFFER) == GL_FRAMEBUFFER_COMPLETE;
|
||||
}
|
||||
|
||||
virtual void deleteFBO(GLuint framebuffer, GLuint depth_stencil, GLuint img)
|
||||
virtual void deleteFBO(GLuint framebuffer, GLuint depth_stencil)
|
||||
{
|
||||
gl.deleteTexture(img);
|
||||
if (depth_stencil != 0)
|
||||
glDeleteRenderbuffers(1, &depth_stencil);
|
||||
if (framebuffer != 0)
|
||||
@@ -218,7 +189,7 @@ struct FramebufferStrategyCorePacked : public FramebufferStrategyCore
|
||||
|
||||
struct FramebufferStrategyPackedEXT : public FramebufferStrategy
|
||||
{
|
||||
virtual GLenum createFBO(GLuint &framebuffer, GLuint &img, int width, int height, Canvas::TextureType texture_type)
|
||||
virtual GLenum createFBO(GLuint &framebuffer, GLuint texture)
|
||||
{
|
||||
GLint current_fbo;
|
||||
glGetIntegerv(GL_DRAW_FRAMEBUFFER_BINDING_EXT, ¤t_fbo);
|
||||
@@ -227,32 +198,8 @@ struct FramebufferStrategyPackedEXT : public FramebufferStrategy
|
||||
glGenFramebuffersEXT(1, &framebuffer);
|
||||
glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, framebuffer);
|
||||
|
||||
// generate texture save target
|
||||
GLint internalFormat;
|
||||
GLenum format;
|
||||
switch (texture_type)
|
||||
{
|
||||
case Canvas::TYPE_HDR:
|
||||
internalFormat = GL_RGBA16F;
|
||||
format = GL_FLOAT;
|
||||
break;
|
||||
case Canvas::TYPE_NORMAL:
|
||||
default:
|
||||
internalFormat = GL_RGBA;
|
||||
format = GL_UNSIGNED_BYTE;
|
||||
}
|
||||
|
||||
glGenTextures(1, &img);
|
||||
gl.bindTexture(img);
|
||||
|
||||
Texture::Filter filter = Texture::getDefaultFilter();
|
||||
gl.setTextureFilter(filter);
|
||||
|
||||
glTexImage2D(GL_TEXTURE_2D, 0, internalFormat, width, height,
|
||||
0, GL_RGBA, format, NULL);
|
||||
gl.bindTexture(0);
|
||||
glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT,
|
||||
GL_TEXTURE_2D, img, 0);
|
||||
GL_TEXTURE_2D, texture, 0);
|
||||
|
||||
// check status
|
||||
GLenum status = glCheckFramebufferStatusEXT(GL_FRAMEBUFFER_EXT);
|
||||
@@ -279,9 +226,8 @@ struct FramebufferStrategyPackedEXT : public FramebufferStrategy
|
||||
return glCheckFramebufferStatusEXT(GL_FRAMEBUFFER_EXT) == GL_FRAMEBUFFER_COMPLETE_EXT;
|
||||
}
|
||||
|
||||
virtual void deleteFBO(GLuint framebuffer, GLuint depth_stencil, GLuint img)
|
||||
virtual void deleteFBO(GLuint framebuffer, GLuint depth_stencil)
|
||||
{
|
||||
gl.deleteTexture(img);
|
||||
if (depth_stencil != 0)
|
||||
glDeleteRenderbuffersEXT(1, &depth_stencil);
|
||||
if (framebuffer != 0)
|
||||
@@ -347,9 +293,9 @@ struct FramebufferStrategyEXT : public FramebufferStrategyPackedEXT
|
||||
|
||||
bool isSupported()
|
||||
{
|
||||
GLuint fb = 0, stencil = 0, img = 0;
|
||||
GLenum status = createFBO(fb, img, 2, 2, Canvas::TYPE_NORMAL);
|
||||
deleteFBO(fb, stencil, img);
|
||||
GLuint fb = 0, stencil = 0;
|
||||
GLenum status = createFBO(fb, 0);
|
||||
deleteFBO(fb, stencil);
|
||||
return status == GL_FRAMEBUFFER_COMPLETE;
|
||||
}
|
||||
};
|
||||
@@ -391,8 +337,8 @@ static int maxDrawBuffers = 0;
|
||||
|
||||
Canvas::Canvas(int width, int height, TextureType texture_type)
|
||||
: fbo(0)
|
||||
, texture(0)
|
||||
, depth_stencil(0)
|
||||
, img(0)
|
||||
, texture_type(texture_type)
|
||||
{
|
||||
this->width = width;
|
||||
@@ -437,7 +383,7 @@ Canvas::~Canvas()
|
||||
|
||||
bool Canvas::loadVolatile()
|
||||
{
|
||||
fbo = depth_stencil = img = 0;
|
||||
fbo = depth_stencil = texture = 0;
|
||||
|
||||
// glTexImage2D is guaranteed to error in this case.
|
||||
if (width > gl.getMaxTextureSize() || height > gl.getMaxTextureSize())
|
||||
@@ -446,20 +392,59 @@ bool Canvas::loadVolatile()
|
||||
return false;
|
||||
}
|
||||
|
||||
status = strategy->createFBO(fbo, img, width, height, texture_type);
|
||||
if (status != GL_FRAMEBUFFER_COMPLETE)
|
||||
return false;
|
||||
glGenTextures(1, &texture);
|
||||
gl.bindTexture(texture);
|
||||
|
||||
setFilter(filter);
|
||||
setWrap(wrap);
|
||||
|
||||
GLint internalformat;
|
||||
GLenum textype;
|
||||
switch (texture_type)
|
||||
{
|
||||
case TYPE_HDR:
|
||||
internalformat = GL_RGBA16F;
|
||||
textype = GL_FLOAT;
|
||||
break;
|
||||
case TYPE_NORMAL:
|
||||
default:
|
||||
internalformat = GL_RGBA8;
|
||||
textype = GL_UNSIGNED_BYTE;
|
||||
}
|
||||
|
||||
while (glGetError() != GL_NO_ERROR)
|
||||
/* Clear the error buffer. */;
|
||||
|
||||
glTexImage2D(GL_TEXTURE_2D,
|
||||
0,
|
||||
internalformat,
|
||||
width, height,
|
||||
0,
|
||||
GL_RGBA,
|
||||
textype,
|
||||
nullptr);
|
||||
|
||||
if (glGetError() != GL_NO_ERROR)
|
||||
{
|
||||
status = GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT;
|
||||
return false;
|
||||
}
|
||||
|
||||
status = strategy->createFBO(fbo, texture);
|
||||
if (status != GL_FRAMEBUFFER_COMPLETE)
|
||||
return false;
|
||||
|
||||
clear(Color(0, 0, 0, 0));
|
||||
return true;
|
||||
}
|
||||
|
||||
void Canvas::unloadVolatile()
|
||||
{
|
||||
strategy->deleteFBO(fbo, depth_stencil, img);
|
||||
fbo = depth_stencil = img = 0;
|
||||
strategy->deleteFBO(fbo, depth_stencil);
|
||||
|
||||
gl.deleteTexture(texture);
|
||||
|
||||
fbo = depth_stencil = texture = 0;
|
||||
|
||||
for (size_t i = 0; i < attachedCanvases.size(); i++)
|
||||
attachedCanvases[i]->release();
|
||||
@@ -513,25 +498,25 @@ void Canvas::drawq(Quad *quad, float x, float y, float angle, float sx, float sy
|
||||
void Canvas::setFilter(const Texture::Filter &f)
|
||||
{
|
||||
filter = f;
|
||||
gl.bindTexture(img);
|
||||
gl.bindTexture(texture);
|
||||
gl.setTextureFilter(filter);
|
||||
}
|
||||
|
||||
void Canvas::setWrap(const Texture::Wrap &w)
|
||||
{
|
||||
wrap = w;
|
||||
gl.bindTexture(img);
|
||||
gl.bindTexture(texture);
|
||||
gl.setTextureWrap(wrap);
|
||||
}
|
||||
|
||||
GLuint Canvas::getGLTexture() const
|
||||
{
|
||||
return img;
|
||||
return texture;
|
||||
}
|
||||
|
||||
void Canvas::predraw() const
|
||||
{
|
||||
gl.bindTexture(img);
|
||||
gl.bindTexture(texture);
|
||||
}
|
||||
|
||||
void Canvas::setupGrab()
|
||||
|
||||
@@ -113,8 +113,8 @@ public:
|
||||
private:
|
||||
|
||||
GLuint fbo;
|
||||
GLuint texture;
|
||||
GLuint depth_stencil;
|
||||
GLuint img;
|
||||
|
||||
TextureType texture_type;
|
||||
|
||||
|
||||
@@ -46,6 +46,7 @@ Font::Font(love::font::Rasterizer *r, const Texture::Filter &filter)
|
||||
, lineHeight(1)
|
||||
, mSpacing(1)
|
||||
, filter(filter)
|
||||
, useSpacesAsTab(false)
|
||||
{
|
||||
this->filter.mipmap = Texture::FILTER_NONE;
|
||||
|
||||
@@ -67,13 +68,16 @@ Font::Font(love::font::Rasterizer *r, const Texture::Filter &filter)
|
||||
textureWidth = TEXTURE_WIDTHS[textureSizeIndex];
|
||||
textureHeight = TEXTURE_HEIGHTS[textureSizeIndex];
|
||||
|
||||
love::font::GlyphData *gd = 0;
|
||||
love::font::GlyphData *gd = nullptr;
|
||||
|
||||
try
|
||||
{
|
||||
gd = r->getGlyphData(32);
|
||||
gd = r->getGlyphData(32); // Space character.
|
||||
type = (gd->getFormat() == love::font::GlyphData::FORMAT_LUMINANCE_ALPHA) ? FONT_TRUETYPE : FONT_IMAGE;
|
||||
|
||||
if (!r->hasGlyph(9)) // No tab character in the Rasterizer.
|
||||
useSpacesAsTab = true;
|
||||
|
||||
loadVolatile();
|
||||
}
|
||||
catch (love::Exception &)
|
||||
@@ -172,7 +176,26 @@ void Font::createTexture()
|
||||
|
||||
Font::Glyph *Font::addGlyph(uint32 glyph)
|
||||
{
|
||||
love::font::GlyphData *gd = rasterizer->getGlyphData(glyph);
|
||||
love::font::GlyphData *gd = nullptr;
|
||||
|
||||
// Use spaces for the tab 'glyph'.
|
||||
if (glyph == 9 && useSpacesAsTab)
|
||||
{
|
||||
love::font::GlyphData *spacegd = rasterizer->getGlyphData(32);
|
||||
|
||||
love::font::GlyphMetrics gm = {};
|
||||
gm.advance = spacegd->getAdvance() * SPACES_PER_TAB;
|
||||
gm.bearingX = spacegd->getBearingX();
|
||||
gm.bearingY = spacegd->getBearingY();
|
||||
love::font::GlyphData::Format f = spacegd->getFormat();
|
||||
|
||||
spacegd->release();
|
||||
|
||||
gd = new love::font::GlyphData(glyph, gm, f);
|
||||
}
|
||||
else
|
||||
gd = rasterizer->getGlyphData(glyph);
|
||||
|
||||
int w = gd->getWidth();
|
||||
int h = gd->getHeight();
|
||||
|
||||
@@ -186,7 +209,15 @@ Font::Glyph *Font::addGlyph(uint32 glyph)
|
||||
if (textureY + h + TEXTURE_PADDING > textureHeight)
|
||||
{
|
||||
// totally out of space - new texture!
|
||||
createTexture();
|
||||
try
|
||||
{
|
||||
createTexture();
|
||||
}
|
||||
catch (love::Exception &)
|
||||
{
|
||||
gd->release();
|
||||
throw;
|
||||
}
|
||||
}
|
||||
|
||||
Glyph *g = new Glyph;
|
||||
|
||||
@@ -202,14 +202,19 @@ private:
|
||||
FontType type;
|
||||
Texture::Filter filter;
|
||||
|
||||
int textureX, textureY;
|
||||
int rowHeight;
|
||||
|
||||
bool useSpacesAsTab;
|
||||
|
||||
static const int NUM_TEXTURE_SIZES = 7;
|
||||
static const int TEXTURE_WIDTHS[NUM_TEXTURE_SIZES];
|
||||
static const int TEXTURE_HEIGHTS[NUM_TEXTURE_SIZES];
|
||||
|
||||
static const int TEXTURE_PADDING = 1;
|
||||
|
||||
int textureX, textureY;
|
||||
int rowHeight;
|
||||
// This will be used if the Rasterizer doesn't have a tab character itself.
|
||||
static const int SPACES_PER_TAB = 4;
|
||||
|
||||
}; // Font
|
||||
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -119,6 +119,7 @@ ParticleSystem::ParticleSystem(const ParticleSystem &p)
|
||||
, emissionRate(p.emissionRate)
|
||||
, emitCounter(0.0f)
|
||||
, position(p.position)
|
||||
, prevPosition(p.prevPosition)
|
||||
, areaSpreadDistribution(p.areaSpreadDistribution)
|
||||
, areaSpread(p.areaSpread)
|
||||
, lifetime(p.lifetime)
|
||||
@@ -215,14 +216,14 @@ uint32 ParticleSystem::getBufferSize() const
|
||||
return maxParticles;
|
||||
}
|
||||
|
||||
void ParticleSystem::addParticle()
|
||||
void ParticleSystem::addParticle(float t)
|
||||
{
|
||||
if (isFull())
|
||||
return;
|
||||
|
||||
// Gets a free particle and updates the allocation pointer.
|
||||
particle *p = pFree++;
|
||||
initParticle(p);
|
||||
initParticle(p, t);
|
||||
|
||||
switch (insertMode)
|
||||
{
|
||||
@@ -241,10 +242,13 @@ void ParticleSystem::addParticle()
|
||||
activeParticles++;
|
||||
}
|
||||
|
||||
void ParticleSystem::initParticle(particle *p)
|
||||
void ParticleSystem::initParticle(particle *p, float t)
|
||||
{
|
||||
float min,max;
|
||||
|
||||
// Linearly interpolate between the previous and current emitter position.
|
||||
love::Vector pos = prevPosition + (position - prevPosition) * t;
|
||||
|
||||
min = particleLifeMin;
|
||||
max = particleLifeMax;
|
||||
if (min == max)
|
||||
@@ -253,8 +257,8 @@ void ParticleSystem::initParticle(particle *p)
|
||||
p->life = (float) rng.random(min, max);
|
||||
p->lifetime = p->life;
|
||||
|
||||
p->position[0] = position.getX();
|
||||
p->position[1] = position.getY();
|
||||
p->position[0] = pos.x;
|
||||
p->position[1] = pos.y;
|
||||
|
||||
switch (areaSpreadDistribution)
|
||||
{
|
||||
@@ -275,7 +279,7 @@ void ParticleSystem::initParticle(particle *p)
|
||||
max = direction + spread/2.0f;
|
||||
p->direction = (float) rng.random(min, max);
|
||||
|
||||
p->origin = position;
|
||||
p->origin = pos;
|
||||
|
||||
min = speedMin;
|
||||
max = speedMax;
|
||||
@@ -758,7 +762,7 @@ void ParticleSystem::emit(uint32 num)
|
||||
num = std::min(num, maxParticles - activeParticles);
|
||||
|
||||
while(num--)
|
||||
addParticle();
|
||||
addParticle(1.0f);
|
||||
}
|
||||
|
||||
bool ParticleSystem::isActive() const
|
||||
@@ -860,25 +864,6 @@ void ParticleSystem::update(float dt)
|
||||
if (pMem == nullptr || dt == 0.0f)
|
||||
return;
|
||||
|
||||
// Make some more particles.
|
||||
if (active)
|
||||
{
|
||||
float rate = 1.0f / emissionRate; // the amount of time between each particle emit
|
||||
emitCounter += dt;
|
||||
while (emitCounter > rate)
|
||||
{
|
||||
addParticle();
|
||||
emitCounter -= rate;
|
||||
}
|
||||
/*int particles = (int)(emissionRate * dt);
|
||||
for (int i = 0; i != particles; i++)
|
||||
add();*/
|
||||
|
||||
life -= dt;
|
||||
if (lifetime != -1 && life < 0)
|
||||
stop();
|
||||
}
|
||||
|
||||
// Traverse all particles and update.
|
||||
particle *p = pHead;
|
||||
|
||||
@@ -953,6 +938,28 @@ void ParticleSystem::update(float dt)
|
||||
p = p->next;
|
||||
}
|
||||
}
|
||||
|
||||
// Make some more particles.
|
||||
if (active)
|
||||
{
|
||||
float rate = 1.0f / emissionRate; // the amount of time between each particle emit
|
||||
emitCounter += dt;
|
||||
float total = emitCounter - rate;
|
||||
while (emitCounter > rate)
|
||||
{
|
||||
addParticle(1.0f - (emitCounter - rate) / total);
|
||||
emitCounter -= rate;
|
||||
}
|
||||
/*int particles = (int)(emissionRate * dt);
|
||||
for (int i = 0; i != particles; i++)
|
||||
add();*/
|
||||
|
||||
life -= dt;
|
||||
if (lifetime != -1 && life < 0)
|
||||
stop();
|
||||
}
|
||||
|
||||
prevPosition = position;
|
||||
}
|
||||
|
||||
bool ParticleSystem::getConstant(const char *in, AreaSpreadDistribution &out)
|
||||
|
||||
@@ -558,6 +558,7 @@ protected:
|
||||
|
||||
// The relative position of the particle emitter.
|
||||
love::Vector position;
|
||||
love::Vector prevPosition;
|
||||
|
||||
// Emission area spread.
|
||||
AreaSpreadDistribution areaSpreadDistribution;
|
||||
@@ -614,11 +615,11 @@ protected:
|
||||
void createBuffers(size_t size);
|
||||
void deleteBuffers();
|
||||
|
||||
void addParticle();
|
||||
void addParticle(float t);
|
||||
particle *removeParticle(particle *p);
|
||||
|
||||
// Called by addParticle.
|
||||
void initParticle(particle *p);
|
||||
void initParticle(particle *p, float t);
|
||||
void insertTop(particle *p);
|
||||
void insertBottom(particle *p);
|
||||
void insertRandom(particle *p);
|
||||
|
||||
@@ -127,6 +127,11 @@ VBO::VBO(size_t size, GLenum target, GLenum usage, MemoryBacking backing)
|
||||
if (!(GLAD_ARB_vertex_buffer_object || GLAD_VERSION_1_5 || GLAD_ES_VERSION_2_0))
|
||||
throw love::Exception("Not supported");
|
||||
|
||||
// FIXME:
|
||||
// ES2 can't do glGetBufferSubData.
|
||||
if (GLAD_ES_VERSION_2_0)
|
||||
backing = BACKING_FULL;
|
||||
|
||||
if (getMemoryBacking() == BACKING_FULL)
|
||||
memory_map = malloc(getSize());
|
||||
|
||||
|
||||
@@ -34,22 +34,21 @@ Canvas *luax_checkcanvas(lua_State *L, int idx)
|
||||
|
||||
int w_Canvas_renderTo(lua_State *L)
|
||||
{
|
||||
// As startGrab() clears the framebuffer, better not allow
|
||||
// grabbing inside another grabbing
|
||||
if (Canvas::current != NULL)
|
||||
{
|
||||
Canvas::bindDefaultCanvas();
|
||||
return luaL_error(L, "Current render target not the default canvas!");
|
||||
}
|
||||
|
||||
Canvas *canvas = luax_checkcanvas(L, 1);
|
||||
luaL_checktype(L, 2, LUA_TFUNCTION);
|
||||
|
||||
// Save the current Canvas so we can restore it when we're done.
|
||||
Canvas *oldcanvas = Canvas::current;
|
||||
|
||||
EXCEPT_GUARD(canvas->startGrab();)
|
||||
|
||||
lua_settop(L, 2); // make sure the function is on top of the stack
|
||||
lua_call(L, 0, 0);
|
||||
canvas->stopGrab();
|
||||
|
||||
if (oldcanvas != nullptr)
|
||||
oldcanvas->startGrab(oldcanvas->getAttachedCanvases());
|
||||
else
|
||||
Canvas::bindDefaultCanvas();
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1152,8 +1152,9 @@ int w_line(lua_State *L)
|
||||
args = lua_objlen(L, 1);
|
||||
is_table = true;
|
||||
}
|
||||
|
||||
if (args % 2 != 0)
|
||||
return luaL_error(L, "Number of vertices must be a multiple of two");
|
||||
return luaL_error(L, "Number of vertex components must be a multiple of two");
|
||||
else if (args < 4)
|
||||
return luaL_error(L, "Need at least two vertices to draw a line");
|
||||
|
||||
@@ -1254,7 +1255,7 @@ int w_polygon(lua_State *L)
|
||||
}
|
||||
|
||||
if (args % 2 != 0)
|
||||
return luaL_error(L, "Number of vertices must be a multiple of two");
|
||||
return luaL_error(L, "Number of vertex components must be a multiple of two");
|
||||
else if (args < 6)
|
||||
return luaL_error(L, "Need at least three vertices to draw a polygon");
|
||||
|
||||
|
||||
@@ -175,6 +175,7 @@ StringMap<Keyboard::Key, Keyboard::KEY_MAX_ENUM>::Entry Keyboard::keyEntries[] =
|
||||
{"execute", Keyboard::KEY_EXECUTE},
|
||||
{"help", Keyboard::KEY_HELP},
|
||||
{"menu", Keyboard::KEY_MENU},
|
||||
{"search", Keyboard::KEY_SEARCH},
|
||||
{"select", Keyboard::KEY_SELECT},
|
||||
{"stop", Keyboard::KEY_STOP},
|
||||
{"again", Keyboard::KEY_AGAIN},
|
||||
|
||||
@@ -175,6 +175,7 @@ public:
|
||||
KEY_EXECUTE,
|
||||
KEY_HELP,
|
||||
KEY_MENU,
|
||||
KEY_SEARCH,
|
||||
KEY_SELECT,
|
||||
KEY_STOP,
|
||||
KEY_AGAIN,
|
||||
|
||||
@@ -219,6 +219,7 @@ std::map<Keyboard::Key, SDL_Keycode> Keyboard::createKeyMap()
|
||||
k[Keyboard::KEY_EXECUTE] = SDLK_EXECUTE;
|
||||
k[Keyboard::KEY_HELP] = SDLK_HELP;
|
||||
k[Keyboard::KEY_MENU] = SDLK_MENU;
|
||||
k[Keyboard::KEY_SEARCH] = SDLK_AC_SEARCH;
|
||||
k[Keyboard::KEY_SELECT] = SDLK_SELECT;
|
||||
k[Keyboard::KEY_STOP] = SDLK_STOP;
|
||||
k[Keyboard::KEY_AGAIN] = SDLK_AGAIN;
|
||||
|
||||
@@ -97,6 +97,9 @@ extern "C"
|
||||
#if defined(LOVE_ENABLE_THREAD)
|
||||
extern int luaopen_love_thread(lua_State*);
|
||||
#endif
|
||||
#if defined(LOVE_ENABLE_TOUCH)
|
||||
extern int luaopen_love_touch(lua_State*);
|
||||
#endif
|
||||
#if defined(LOVE_ENABLE_WINDOW)
|
||||
extern int luaopen_love_window(lua_State*);
|
||||
#endif
|
||||
@@ -149,6 +152,9 @@ static const luaL_Reg modules[] = {
|
||||
#if defined(LOVE_ENABLE_THREAD)
|
||||
{ "love.thread", luaopen_love_thread },
|
||||
#endif
|
||||
#if defined(LOVE_ENABLE_TOUCH)
|
||||
{ "love.touch", luaopen_love_touch },
|
||||
#endif
|
||||
#if defined(LOVE_ENABLE_WINDOW)
|
||||
{ "love.window", luaopen_love_window },
|
||||
#endif
|
||||
@@ -207,6 +213,8 @@ int luaopen_love(lua_State * L)
|
||||
lua_pushstring(L, "Windows");
|
||||
#elif defined(LOVE_MACOSX)
|
||||
lua_pushstring(L, "OS X");
|
||||
#elif defined(LOVE_ANDROID)
|
||||
lua_pushstring(L, "Android");
|
||||
#elif defined(LOVE_LINUX)
|
||||
lua_pushstring(L, "Linux");
|
||||
#else
|
||||
|
||||
@@ -32,6 +32,39 @@ namespace mouse
|
||||
namespace sdl
|
||||
{
|
||||
|
||||
// SDL reports mouse coordinates in the window coordinate system in OS X, but
|
||||
// we want them in pixel coordinates (may be different with high-DPI enabled.)
|
||||
static void windowToPixelCoords(int *x, int *y)
|
||||
{
|
||||
double scale = 1.0;
|
||||
|
||||
love::window::Window *window = love::window::sdl::Window::getSingleton();
|
||||
if (window != nullptr)
|
||||
scale = window->getPixelScale();
|
||||
|
||||
if (x != nullptr)
|
||||
*x = int(double(*x) * scale);
|
||||
|
||||
if (y != nullptr)
|
||||
*y = int(double(*y) * scale);
|
||||
}
|
||||
|
||||
// And vice versa for setting mouse coordinates.
|
||||
static void pixelToWindowCoords(int *x, int *y)
|
||||
{
|
||||
double scale = 1.0;
|
||||
|
||||
love::window::Window *window = love::window::sdl::Window::getSingleton();
|
||||
if (window != nullptr)
|
||||
scale = window->getPixelScale();
|
||||
|
||||
if (x != nullptr)
|
||||
*x = int(double(*x) / scale);
|
||||
|
||||
if (y != nullptr)
|
||||
*y = int(double(*y) / scale);
|
||||
}
|
||||
|
||||
const char *Mouse::getName() const
|
||||
{
|
||||
return "love.mouse.sdl";
|
||||
@@ -98,30 +131,40 @@ love::mouse::Cursor *Mouse::getCursor() const
|
||||
int Mouse::getX() const
|
||||
{
|
||||
int x;
|
||||
SDL_GetMouseState(&x, 0);
|
||||
SDL_GetMouseState(&x, nullptr);
|
||||
windowToPixelCoords(&x, nullptr);
|
||||
|
||||
return x;
|
||||
}
|
||||
|
||||
int Mouse::getY() const
|
||||
{
|
||||
int y;
|
||||
SDL_GetMouseState(0, &y);
|
||||
SDL_GetMouseState(nullptr, &y);
|
||||
windowToPixelCoords(nullptr, &y);
|
||||
|
||||
return y;
|
||||
}
|
||||
|
||||
void Mouse::getPosition(int &x, int &y) const
|
||||
{
|
||||
SDL_GetMouseState(&x, &y);
|
||||
int mx, my;
|
||||
SDL_GetMouseState(&mx, &my);
|
||||
windowToPixelCoords(&mx, &my);
|
||||
|
||||
x = mx;
|
||||
y = my;
|
||||
}
|
||||
|
||||
void Mouse::setPosition(int x, int y)
|
||||
{
|
||||
love::window::Window *window = love::window::sdl::Window::getSingleton();
|
||||
|
||||
SDL_Window *handle = NULL;
|
||||
SDL_Window *handle = nullptr;
|
||||
if (window)
|
||||
handle = (SDL_Window *) window->getHandle();
|
||||
|
||||
pixelToWindowCoords(&x, &y);
|
||||
SDL_WarpMouseInWindow(handle, x, y);
|
||||
}
|
||||
|
||||
|
||||
@@ -93,8 +93,9 @@ EdgeShape *Physics::newEdgeShape(float x1, float y1, float x2, float y2)
|
||||
int Physics::newPolygonShape(lua_State *L)
|
||||
{
|
||||
int argc = lua_gettop(L);
|
||||
if (argc%2 != 0)
|
||||
return luaL_error(L, "Number of vertices must be a multiple of two.");
|
||||
if (argc % 2 != 0)
|
||||
return luaL_error(L, "Number of vertex components must be a multiple of two.");
|
||||
|
||||
// 3 to 8 (b2_maxPolygonVertices) vertices
|
||||
int vcount = argc / 2;
|
||||
if (vcount < 3)
|
||||
|
||||
@@ -31,6 +31,8 @@ std::string System::getOS() const
|
||||
return "OS X";
|
||||
#elif LOVE_WINDOWS
|
||||
return "Windows";
|
||||
#elif LOVE_ANDROID
|
||||
return "Android";
|
||||
#elif LOVE_LINUX
|
||||
return "Linux";
|
||||
#else
|
||||
|
||||
@@ -110,15 +110,20 @@ void LuaThread::onError()
|
||||
if (!event)
|
||||
return;
|
||||
|
||||
std::vector<Variant *> vargs;
|
||||
|
||||
Proxy p;
|
||||
p.flags = THREAD_THREAD_T;
|
||||
p.data = this;
|
||||
|
||||
Variant *arg1 = new Variant(THREAD_THREAD_ID, &p);
|
||||
Variant *arg2 = new Variant(error.c_str(), error.length());
|
||||
event::Message *msg = new event::Message("threaderror", arg1, arg2);
|
||||
arg1->release();
|
||||
arg2->release();
|
||||
vargs.push_back(new Variant(THREAD_THREAD_ID, &p));
|
||||
vargs.push_back(new Variant(error.c_str(), error.length()));
|
||||
|
||||
event::Message *msg = new event::Message("threaderror", vargs);
|
||||
|
||||
for (auto it = vargs.begin(); it != vargs.end(); ++it)
|
||||
(*it)->release();
|
||||
|
||||
|
||||
event->push(msg);
|
||||
msg->release();
|
||||
|
||||
@@ -0,0 +1,68 @@
|
||||
/**
|
||||
* Copyright (c) 2006-2014 LOVE Development Team
|
||||
*
|
||||
* This software is provided 'as-is', without any express or implied
|
||||
* warranty. In no event will the authors be held liable for any damages
|
||||
* arising from the use of this software.
|
||||
*
|
||||
* Permission is granted to anyone to use this software for any purpose,
|
||||
* including commercial applications, and to alter it and redistribute it
|
||||
* freely, subject to the following restrictions:
|
||||
*
|
||||
* 1. The origin of this software must not be misrepresented; you must not
|
||||
* claim that you wrote the original software. If you use this software
|
||||
* in a product, an acknowledgment in the product documentation would be
|
||||
* appreciated but is not required.
|
||||
* 2. Altered source versions must be plainly marked as such, and must not be
|
||||
* misrepresented as being the original software.
|
||||
* 3. This notice may not be removed or altered from any source distribution.
|
||||
**/
|
||||
|
||||
#ifndef LOVE_TOUCH_TOUCH_H
|
||||
#define LOVE_TOUCH_TOUCH_H
|
||||
|
||||
// LOVE
|
||||
#include "common/int.h"
|
||||
#include "common/Object.h"
|
||||
#include "common/Module.h"
|
||||
|
||||
// C++
|
||||
#include <vector>
|
||||
#include <limits>
|
||||
|
||||
namespace love
|
||||
{
|
||||
namespace touch
|
||||
{
|
||||
|
||||
class Touch : public Module
|
||||
{
|
||||
public:
|
||||
|
||||
struct TouchInfo
|
||||
{
|
||||
int64 id; // Only unique for the duration of the touch-press.
|
||||
float x; // Normalized to [0, 1].
|
||||
float y; // Normalized to [0, 1].
|
||||
float pressure; // Normalized to [0, 1].
|
||||
};
|
||||
|
||||
virtual ~Touch() {}
|
||||
|
||||
/**
|
||||
* Gets the number of current touch presses.
|
||||
**/
|
||||
virtual int getTouchCount() const = 0;
|
||||
|
||||
/**
|
||||
* Gets information about a touch press. The index is unstable and should
|
||||
* not be relied on being the same in between calls.
|
||||
**/
|
||||
virtual TouchInfo getTouch(int index) const = 0;
|
||||
|
||||
}; // Touch
|
||||
|
||||
} // touch
|
||||
} // love
|
||||
|
||||
#endif // LOVE_TOUCH_TOUCH_H
|
||||
@@ -0,0 +1,93 @@
|
||||
/**
|
||||
* Copyright (c) 2006-2014 LOVE Development Team
|
||||
*
|
||||
* This software is provided 'as-is', without any express or implied
|
||||
* warranty. In no event will the authors be held liable for any damages
|
||||
* arising from the use of this software.
|
||||
*
|
||||
* Permission is granted to anyone to use this software for any purpose,
|
||||
* including commercial applications, and to alter it and redistribute it
|
||||
* freely, subject to the following restrictions:
|
||||
*
|
||||
* 1. The origin of this software must not be misrepresented; you must not
|
||||
* claim that you wrote the original software. If you use this software
|
||||
* in a product, an acknowledgment in the product documentation would be
|
||||
* appreciated but is not required.
|
||||
* 2. Altered source versions must be plainly marked as such, and must not be
|
||||
* misrepresented as being the original software.
|
||||
* 3. This notice may not be removed or altered from any source distribution.
|
||||
**/
|
||||
|
||||
// LOVE
|
||||
#include "common/config.h"
|
||||
#include "common/Exception.h"
|
||||
#include "Touch.h"
|
||||
|
||||
// SDL
|
||||
#include <SDL_touch.h>
|
||||
|
||||
namespace love
|
||||
{
|
||||
namespace touch
|
||||
{
|
||||
namespace sdl
|
||||
{
|
||||
|
||||
int Touch::getTouchCount() const
|
||||
{
|
||||
int count = 0;
|
||||
|
||||
for (int i = 0; i < SDL_GetNumTouchDevices(); i++)
|
||||
count += SDL_GetNumTouchFingers(SDL_GetTouchDevice(i));
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
Touch::TouchInfo Touch::getTouch(int index) const
|
||||
{
|
||||
SDL_TouchID deviceID = 0;
|
||||
|
||||
int touchcount = 0;
|
||||
int fingerindex = -1;
|
||||
|
||||
// Find the device and finger index from the given external index.
|
||||
for (int i = 0; i < SDL_GetNumTouchDevices(); i++)
|
||||
{
|
||||
deviceID = SDL_GetTouchDevice(i);
|
||||
int fingercount = SDL_GetNumTouchFingers(deviceID);
|
||||
|
||||
if (index < touchcount + fingercount)
|
||||
{
|
||||
fingerindex = index - touchcount;
|
||||
break;
|
||||
}
|
||||
|
||||
touchcount += fingercount;
|
||||
}
|
||||
|
||||
if (fingerindex < 0)
|
||||
throw love::Exception("Invalid touch index.");
|
||||
|
||||
SDL_Finger *finger = SDL_GetTouchFinger(deviceID, fingerindex);
|
||||
|
||||
if (finger == nullptr)
|
||||
throw love::Exception("Cannot get touch info.");
|
||||
|
||||
TouchInfo info = {};
|
||||
|
||||
info.id = (int64) finger->id;
|
||||
info.x = finger->x;
|
||||
info.y = finger->y;
|
||||
info.pressure = finger->pressure;
|
||||
|
||||
return info;
|
||||
}
|
||||
|
||||
const char *Touch::getName() const
|
||||
{
|
||||
return "love.touch.sdl";
|
||||
}
|
||||
|
||||
} // sdl
|
||||
} // touch
|
||||
} // love
|
||||
@@ -0,0 +1,52 @@
|
||||
/**
|
||||
* Copyright (c) 2006-2014 LOVE Development Team
|
||||
*
|
||||
* This software is provided 'as-is', without any express or implied
|
||||
* warranty. In no event will the authors be held liable for any damages
|
||||
* arising from the use of this software.
|
||||
*
|
||||
* Permission is granted to anyone to use this software for any purpose,
|
||||
* including commercial applications, and to alter it and redistribute it
|
||||
* freely, subject to the following restrictions:
|
||||
*
|
||||
* 1. The origin of this software must not be misrepresented; you must not
|
||||
* claim that you wrote the original software. If you use this software
|
||||
* in a product, an acknowledgment in the product documentation would be
|
||||
* appreciated but is not required.
|
||||
* 2. Altered source versions must be plainly marked as such, and must not be
|
||||
* misrepresented as being the original software.
|
||||
* 3. This notice may not be removed or altered from any source distribution.
|
||||
**/
|
||||
|
||||
#ifndef LOVE_TOUCH_SDL_TOUCH_H
|
||||
#define LOVE_TOUCH_SDL_TOUCH_H
|
||||
|
||||
// LOVE
|
||||
#include "touch/Touch.h"
|
||||
|
||||
namespace love
|
||||
{
|
||||
namespace touch
|
||||
{
|
||||
namespace sdl
|
||||
{
|
||||
|
||||
class Touch : public love::touch::Touch
|
||||
{
|
||||
public:
|
||||
|
||||
virtual ~Touch() {}
|
||||
|
||||
virtual int getTouchCount() const;
|
||||
virtual TouchInfo getTouch(int index) const;
|
||||
|
||||
// Implements Module.
|
||||
virtual const char *getName() const;
|
||||
|
||||
}; // Touch
|
||||
|
||||
} // sdl
|
||||
} // touch
|
||||
} // love
|
||||
|
||||
#endif // LOVE_TOUCH_SDL_TOUCH_H
|
||||
@@ -0,0 +1,84 @@
|
||||
/**
|
||||
* Copyright (c) 2006-2014 LOVE Development Team
|
||||
*
|
||||
* This software is provided 'as-is', without any express or implied
|
||||
* warranty. In no event will the authors be held liable for any damages
|
||||
* arising from the use of this software.
|
||||
*
|
||||
* Permission is granted to anyone to use this software for any purpose,
|
||||
* including commercial applications, and to alter it and redistribute it
|
||||
* freely, subject to the following restrictions:
|
||||
*
|
||||
* 1. The origin of this software must not be misrepresented; you must not
|
||||
* claim that you wrote the original software. If you use this software
|
||||
* in a product, an acknowledgment in the product documentation would be
|
||||
* appreciated but is not required.
|
||||
* 2. Altered source versions must be plainly marked as such, and must not be
|
||||
* misrepresented as being the original software.
|
||||
* 3. This notice may not be removed or altered from any source distribution.
|
||||
**/
|
||||
|
||||
#include "common/config.h"
|
||||
|
||||
// LOVE
|
||||
#include "wrap_Touch.h"
|
||||
|
||||
#include "sdl/Touch.h"
|
||||
|
||||
namespace love
|
||||
{
|
||||
namespace touch
|
||||
{
|
||||
|
||||
static Touch *instance = nullptr;
|
||||
|
||||
int w_getTouchCount(lua_State *L)
|
||||
{
|
||||
lua_pushinteger(L, instance->getTouchCount());
|
||||
return 1;
|
||||
}
|
||||
|
||||
int w_getTouch(lua_State *L)
|
||||
{
|
||||
int index = luaL_checkint(L, 1) - 1;
|
||||
|
||||
Touch::TouchInfo info;
|
||||
EXCEPT_GUARD(info = instance->getTouch(index);)
|
||||
|
||||
// Lets hope the ID can be accurately represented in a Lua number...
|
||||
lua_pushnumber(L, (lua_Number) info.id);
|
||||
lua_pushnumber(L, info.x);
|
||||
lua_pushnumber(L, info.y);
|
||||
lua_pushnumber(L, info.pressure);
|
||||
|
||||
return 4;
|
||||
}
|
||||
|
||||
static const luaL_Reg functions[] =
|
||||
{
|
||||
{ "getTouchCount", w_getTouchCount },
|
||||
{ "getTouch", w_getTouch },
|
||||
{ 0, 0 }
|
||||
};
|
||||
|
||||
extern "C" int luaopen_love_touch(lua_State *L)
|
||||
{
|
||||
if (instance == nullptr)
|
||||
{
|
||||
EXCEPT_GUARD(instance = new love::touch::sdl::Touch();)
|
||||
}
|
||||
else
|
||||
instance->retain();
|
||||
|
||||
WrappedModule w;
|
||||
w.module = instance;
|
||||
w.name = "touch";
|
||||
w.flags = MODULE_T;
|
||||
w.functions = functions;
|
||||
w.types = nullptr;
|
||||
|
||||
return luax_register_module(L, w);
|
||||
}
|
||||
|
||||
} // touch
|
||||
} // love
|
||||
@@ -0,0 +1,40 @@
|
||||
/**
|
||||
* Copyright (c) 2006-2014 LOVE Development Team
|
||||
*
|
||||
* This software is provided 'as-is', without any express or implied
|
||||
* warranty. In no event will the authors be held liable for any damages
|
||||
* arising from the use of this software.
|
||||
*
|
||||
* Permission is granted to anyone to use this software for any purpose,
|
||||
* including commercial applications, and to alter it and redistribute it
|
||||
* freely, subject to the following restrictions:
|
||||
*
|
||||
* 1. The origin of this software must not be misrepresented; you must not
|
||||
* claim that you wrote the original software. If you use this software
|
||||
* in a product, an acknowledgment in the product documentation would be
|
||||
* appreciated but is not required.
|
||||
* 2. Altered source versions must be plainly marked as such, and must not be
|
||||
* misrepresented as being the original software.
|
||||
* 3. This notice may not be removed or altered from any source distribution.
|
||||
**/
|
||||
|
||||
#ifndef LOVE_TOUCH_WRAP_TOUCH_H
|
||||
#define LOVE_TOUCH_WRAP_TOUCH_H
|
||||
|
||||
// LOVE
|
||||
#include "Touch.h"
|
||||
#include "common/runtime.h"
|
||||
|
||||
namespace love
|
||||
{
|
||||
namespace touch
|
||||
{
|
||||
|
||||
int w_getTouchCount(lua_State *L);
|
||||
int w_getTouch(lua_State *L);
|
||||
extern "C" LOVE_EXPORT int luaopen_love_touch(lua_State *L);
|
||||
|
||||
} // touch
|
||||
} // love
|
||||
|
||||
#endif // LOVE_TOUCH_WRAP_TOUCH_H
|
||||
@@ -26,19 +26,19 @@ namespace love
|
||||
namespace window
|
||||
{
|
||||
|
||||
Window *Window::singleton = NULL;
|
||||
Window *Window::singleton = nullptr;
|
||||
|
||||
Window::~Window()
|
||||
{
|
||||
if (singleton == this)
|
||||
singleton = NULL;
|
||||
singleton = nullptr;
|
||||
}
|
||||
|
||||
void Window::swapBuffers()
|
||||
{
|
||||
}
|
||||
|
||||
WindowAttributes::WindowAttributes()
|
||||
WindowSettings::WindowSettings()
|
||||
: fullscreen(false)
|
||||
, fstype(Window::FULLSCREEN_TYPE_NORMAL)
|
||||
, vsync(true)
|
||||
@@ -49,6 +49,7 @@ WindowAttributes::WindowAttributes()
|
||||
, borderless(false)
|
||||
, centered(true)
|
||||
, display(0)
|
||||
, highdpi(false)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -62,31 +63,32 @@ bool Window::getConstant(Window::FullscreenType in, const char *&out)
|
||||
return fullscreenTypes.find(in, out);
|
||||
}
|
||||
|
||||
bool Window::getConstant(const char *in, Window::Attribute &out)
|
||||
bool Window::getConstant(const char *in, Window::Setting &out)
|
||||
{
|
||||
return attributes.find(in, out);
|
||||
return settings.find(in, out);
|
||||
}
|
||||
|
||||
bool Window::getConstant(Window::Attribute in, const char *&out)
|
||||
bool Window::getConstant(Window::Setting in, const char *&out)
|
||||
{
|
||||
return attributes.find(in, out);
|
||||
return settings.find(in, out);
|
||||
}
|
||||
|
||||
StringMap<Window::Attribute, Window::ATTRIB_MAX_ENUM>::Entry Window::attributeEntries[] =
|
||||
StringMap<Window::Setting, Window::SETTING_MAX_ENUM>::Entry Window::settingEntries[] =
|
||||
{
|
||||
{"fullscreen", ATTRIB_FULLSCREEN},
|
||||
{"fullscreentype", ATTRIB_FULLSCREEN_TYPE},
|
||||
{"vsync", ATTRIB_VSYNC},
|
||||
{"fsaa", ATTRIB_FSAA},
|
||||
{"resizable", ATTRIB_RESIZABLE},
|
||||
{"minwidth", ATTRIB_MIN_WIDTH},
|
||||
{"minheight", ATTRIB_MIN_HEIGHT},
|
||||
{"borderless", ATTRIB_BORDERLESS},
|
||||
{"centered", ATTRIB_CENTERED},
|
||||
{"display", ATTRIB_DISPLAY}
|
||||
{"fullscreen", SETTING_FULLSCREEN},
|
||||
{"fullscreentype", SETTING_FULLSCREEN_TYPE},
|
||||
{"vsync", SETTING_VSYNC},
|
||||
{"fsaa", SETTING_FSAA},
|
||||
{"resizable", SETTING_RESIZABLE},
|
||||
{"minwidth", SETTING_MIN_WIDTH},
|
||||
{"minheight", SETTING_MIN_HEIGHT},
|
||||
{"borderless", SETTING_BORDERLESS},
|
||||
{"centered", SETTING_CENTERED},
|
||||
{"display", SETTING_DISPLAY},
|
||||
{"highdpi", SETTING_HIGHDPI},
|
||||
};
|
||||
|
||||
StringMap<Window::Attribute, Window::ATTRIB_MAX_ENUM> Window::attributes(Window::attributeEntries, sizeof(Window::attributeEntries));
|
||||
StringMap<Window::Setting, Window::SETTING_MAX_ENUM> Window::settings(Window::settingEntries, sizeof(Window::settingEntries));
|
||||
|
||||
StringMap<Window::FullscreenType, Window::FULLSCREEN_TYPE_MAX_ENUM>::Entry Window::fullscreenTypeEntries[] =
|
||||
{
|
||||
|
||||
@@ -37,26 +37,27 @@ namespace window
|
||||
|
||||
// Forward-declared so it can be used in the class methods. We can't define the
|
||||
// whole thing here because it uses the Window::Type enum.
|
||||
struct WindowAttributes;
|
||||
struct WindowSettings;
|
||||
|
||||
class Window : public Module
|
||||
{
|
||||
public:
|
||||
|
||||
// Types of window attributes.
|
||||
enum Attribute
|
||||
// Different window settings.
|
||||
enum Setting
|
||||
{
|
||||
ATTRIB_FULLSCREEN,
|
||||
ATTRIB_FULLSCREEN_TYPE,
|
||||
ATTRIB_VSYNC,
|
||||
ATTRIB_FSAA,
|
||||
ATTRIB_RESIZABLE,
|
||||
ATTRIB_MIN_WIDTH,
|
||||
ATTRIB_MIN_HEIGHT,
|
||||
ATTRIB_BORDERLESS,
|
||||
ATTRIB_CENTERED,
|
||||
ATTRIB_DISPLAY,
|
||||
ATTRIB_MAX_ENUM
|
||||
SETTING_FULLSCREEN,
|
||||
SETTING_FULLSCREEN_TYPE,
|
||||
SETTING_VSYNC,
|
||||
SETTING_FSAA,
|
||||
SETTING_RESIZABLE,
|
||||
SETTING_MIN_WIDTH,
|
||||
SETTING_MIN_HEIGHT,
|
||||
SETTING_BORDERLESS,
|
||||
SETTING_CENTERED,
|
||||
SETTING_DISPLAY,
|
||||
SETTING_HIGHDPI,
|
||||
SETTING_MAX_ENUM
|
||||
};
|
||||
|
||||
enum FullscreenType
|
||||
@@ -74,8 +75,8 @@ public:
|
||||
|
||||
virtual ~Window();
|
||||
|
||||
virtual bool setWindow(int width = 800, int height = 600, WindowAttributes *attribs = 0) = 0;
|
||||
virtual void getWindow(int &width, int &height, WindowAttributes &attribs) = 0;
|
||||
virtual bool setWindow(int width = 800, int height = 600, WindowSettings *settings = nullptr) = 0;
|
||||
virtual void getWindow(int &width, int &height, WindowSettings &settings) = 0;
|
||||
|
||||
virtual bool setFullscreen(bool fullscreen, FullscreenType fstype) = 0;
|
||||
virtual bool setFullscreen(bool fullscreen) = 0;
|
||||
@@ -113,14 +114,16 @@ public:
|
||||
virtual void setMouseGrab(bool grab) = 0;
|
||||
virtual bool isMouseGrabbed() const = 0;
|
||||
|
||||
virtual double getPixelScale() const = 0;
|
||||
|
||||
virtual const void *getHandle() const = 0;
|
||||
|
||||
//virtual static Window *createSingleton() = 0;
|
||||
//virtual static Window *getSingleton() = 0;
|
||||
// No virtual statics, of course, but you are supposed to implement these statics.
|
||||
|
||||
static bool getConstant(const char *in, Attribute &out);
|
||||
static bool getConstant(Attribute in, const char *&out);
|
||||
static bool getConstant(const char *in, Setting &out);
|
||||
static bool getConstant(Setting in, const char *&out);
|
||||
|
||||
static bool getConstant(const char *in, FullscreenType &out);
|
||||
static bool getConstant(FullscreenType in, const char *&out);
|
||||
@@ -131,17 +134,18 @@ protected:
|
||||
|
||||
private:
|
||||
|
||||
static StringMap<Attribute, ATTRIB_MAX_ENUM>::Entry attributeEntries[];
|
||||
static StringMap<Attribute, ATTRIB_MAX_ENUM> attributes;
|
||||
static StringMap<Setting, SETTING_MAX_ENUM>::Entry settingEntries[];
|
||||
static StringMap<Setting, SETTING_MAX_ENUM> settings;
|
||||
|
||||
static StringMap<FullscreenType, FULLSCREEN_TYPE_MAX_ENUM>::Entry fullscreenTypeEntries[];
|
||||
static StringMap<FullscreenType, FULLSCREEN_TYPE_MAX_ENUM> fullscreenTypes;
|
||||
|
||||
}; // Window
|
||||
|
||||
struct WindowAttributes
|
||||
struct WindowSettings
|
||||
{
|
||||
WindowAttributes();
|
||||
WindowSettings();
|
||||
|
||||
bool fullscreen; // = false
|
||||
Window::FullscreenType fstype; // = FULLSCREEN_TYPE_NORMAL
|
||||
bool vsync; // = true
|
||||
@@ -152,7 +156,9 @@ struct WindowAttributes
|
||||
bool borderless; // = false
|
||||
bool centered; // = true
|
||||
int display; // = 0
|
||||
}; // WindowFlags
|
||||
bool highdpi; // false
|
||||
|
||||
}; // WindowSettings
|
||||
|
||||
} // window
|
||||
} // love
|
||||
|
||||
@@ -28,6 +28,9 @@
|
||||
#include <vector>
|
||||
#include <algorithm>
|
||||
|
||||
// C
|
||||
#include <cstring>
|
||||
|
||||
namespace love
|
||||
{
|
||||
namespace window
|
||||
@@ -63,21 +66,21 @@ Window::~Window()
|
||||
Window::_currentMode::_currentMode()
|
||||
: width(800)
|
||||
, height(600)
|
||||
, attribs()
|
||||
, settings()
|
||||
, icon(0)
|
||||
{
|
||||
}
|
||||
|
||||
bool Window::setWindow(int width, int height, WindowAttributes *attribs)
|
||||
bool Window::setWindow(int width, int height, WindowSettings *settings)
|
||||
{
|
||||
graphics::Graphics *gfx = (graphics::Graphics *) Module::findInstance("love.graphics.");
|
||||
if (gfx)
|
||||
if (gfx != nullptr)
|
||||
gfx->unSetMode();
|
||||
|
||||
WindowAttributes f;
|
||||
WindowSettings f;
|
||||
|
||||
if (attribs)
|
||||
f = *attribs;
|
||||
if (settings)
|
||||
f = *settings;
|
||||
|
||||
f.minwidth = std::max(f.minwidth, 1);
|
||||
f.minheight = std::max(f.minheight, 1);
|
||||
@@ -116,15 +119,28 @@ bool Window::setWindow(int width, int height, WindowAttributes *attribs)
|
||||
if (f.borderless)
|
||||
sdlflags |= SDL_WINDOW_BORDERLESS;
|
||||
|
||||
#if SDL_VERSION_ATLEAST(2,0,1)
|
||||
if (f.highdpi)
|
||||
sdlflags |= SDL_WINDOW_ALLOW_HIGHDPI;
|
||||
#endif
|
||||
|
||||
// Destroy and recreate the window if the dimensions or flags have changed.
|
||||
if (window)
|
||||
{
|
||||
int curdisplay = SDL_GetWindowDisplayIndex(window);
|
||||
Uint32 wflags = SDL_GetWindowFlags(window);
|
||||
wflags &= (SDL_WINDOW_OPENGL | SDL_WINDOW_FULLSCREEN_DESKTOP | SDL_WINDOW_RESIZABLE | SDL_WINDOW_BORDERLESS);
|
||||
|
||||
Uint32 testflags = SDL_WINDOW_OPENGL | SDL_WINDOW_FULLSCREEN_DESKTOP
|
||||
| SDL_WINDOW_RESIZABLE | SDL_WINDOW_BORDERLESS;
|
||||
|
||||
#if SDL_VERSION_ATLEAST(2,0,1)
|
||||
testflags |= SDL_WINDOW_ALLOW_HIGHDPI;
|
||||
#endif
|
||||
|
||||
wflags &= testflags;
|
||||
|
||||
if (sdlflags != wflags || width != curMode.width || height != curMode.height
|
||||
|| f.display != curdisplay || f.fsaa != curMode.attribs.fsaa)
|
||||
|| f.display != curdisplay || f.fsaa != curMode.settings.fsaa)
|
||||
{
|
||||
SDL_DestroyWindow(window);
|
||||
window = 0;
|
||||
@@ -185,11 +201,18 @@ bool Window::setWindow(int width, int height, WindowAttributes *attribs)
|
||||
|
||||
created = true;
|
||||
|
||||
updateAttributes(f);
|
||||
updateSettings(f);
|
||||
|
||||
if (gfx)
|
||||
if (gfx != nullptr)
|
||||
{
|
||||
if (!gfx->setMode(curMode.width, curMode.height))
|
||||
int width = curMode.width;
|
||||
int height = curMode.height;
|
||||
|
||||
#if SDL_VERSION_ATLEAST(2,0,1)
|
||||
SDL_GL_GetDrawableSize(window, &width, &height);
|
||||
#endif
|
||||
|
||||
if (!gfx->setMode(width, height))
|
||||
displayError("Could not set graphics mode", "Unsupported OpenGL version?");
|
||||
}
|
||||
|
||||
@@ -256,8 +279,8 @@ bool Window::setContext(int fsaa, bool vsync)
|
||||
fsaa = (buffers > 0) ? samples : 0;
|
||||
}
|
||||
|
||||
curMode.attribs.fsaa = fsaa;
|
||||
curMode.attribs.vsync = SDL_GL_GetSwapInterval() != 0;
|
||||
curMode.settings.fsaa = fsaa;
|
||||
curMode.settings.vsync = SDL_GL_GetSwapInterval() != 0;
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -276,8 +299,19 @@ void Window::setWindowGLAttributes(int fsaa) const
|
||||
SDL_GL_SetAttribute(SDL_GL_MULTISAMPLEBUFFERS, (fsaa > 0) ? 1 : 0);
|
||||
SDL_GL_SetAttribute(SDL_GL_MULTISAMPLESAMPLES, (fsaa > 0) ? fsaa : 0);
|
||||
|
||||
const char *glesHint = SDL_GetHint("LOVE_GRAPHICS_USE_OPENGLES");
|
||||
if (glesHint && *glesHint == '1')
|
||||
bool tryES2 = false;
|
||||
|
||||
const char *driver = SDL_GetCurrentVideoDriver();
|
||||
|
||||
// We always want to use OpenGL ES on certain video backends.
|
||||
if (driver && (strstr(driver, "RPI") || strstr(driver, "Android") || strstr(driver, "uikit")))
|
||||
tryES2 = true;
|
||||
|
||||
const char *hint = SDL_GetHint("LOVE_GRAPHICS_USE_OPENGLES");
|
||||
if (hint)
|
||||
tryES2 = (*hint) != '0';
|
||||
|
||||
if (tryES2)
|
||||
{
|
||||
// Use OpenGL ES 2+.
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, SDL_GL_CONTEXT_PROFILE_ES);
|
||||
@@ -293,7 +327,7 @@ void Window::setWindowGLAttributes(int fsaa) const
|
||||
}
|
||||
}
|
||||
|
||||
void Window::updateAttributes(const WindowAttributes &newattribs)
|
||||
void Window::updateSettings(const WindowSettings &newsettings)
|
||||
{
|
||||
Uint32 wflags = SDL_GetWindowFlags(window);
|
||||
|
||||
@@ -302,39 +336,45 @@ void Window::updateAttributes(const WindowAttributes &newattribs)
|
||||
|
||||
if ((wflags & SDL_WINDOW_FULLSCREEN_DESKTOP) == SDL_WINDOW_FULLSCREEN_DESKTOP)
|
||||
{
|
||||
curMode.attribs.fullscreen = true;
|
||||
curMode.attribs.fstype = FULLSCREEN_TYPE_DESKTOP;
|
||||
curMode.settings.fullscreen = true;
|
||||
curMode.settings.fstype = FULLSCREEN_TYPE_DESKTOP;
|
||||
}
|
||||
else if ((wflags & SDL_WINDOW_FULLSCREEN) == SDL_WINDOW_FULLSCREEN)
|
||||
{
|
||||
curMode.attribs.fullscreen = true;
|
||||
curMode.attribs.fstype = FULLSCREEN_TYPE_NORMAL;
|
||||
curMode.settings.fullscreen = true;
|
||||
curMode.settings.fstype = FULLSCREEN_TYPE_NORMAL;
|
||||
}
|
||||
else
|
||||
{
|
||||
curMode.attribs.fullscreen = false;
|
||||
curMode.attribs.fstype = newattribs.fstype;
|
||||
curMode.settings.fullscreen = false;
|
||||
curMode.settings.fstype = newsettings.fstype;
|
||||
}
|
||||
|
||||
// The min width/height is set to 0 internally in SDL when in fullscreen.
|
||||
if (curMode.attribs.fullscreen)
|
||||
if (curMode.settings.fullscreen)
|
||||
{
|
||||
curMode.attribs.minwidth = newattribs.minwidth;
|
||||
curMode.attribs.minheight = newattribs.minheight;
|
||||
curMode.settings.minwidth = newsettings.minwidth;
|
||||
curMode.settings.minheight = newsettings.minheight;
|
||||
}
|
||||
else
|
||||
SDL_GetWindowMinimumSize(window, &curMode.attribs.minwidth, &curMode.attribs.minheight);
|
||||
SDL_GetWindowMinimumSize(window, &curMode.settings.minwidth, &curMode.settings.minheight);
|
||||
|
||||
curMode.attribs.resizable = (wflags & SDL_WINDOW_RESIZABLE) != 0;
|
||||
curMode.attribs.borderless = (wflags & SDL_WINDOW_BORDERLESS) != 0;
|
||||
curMode.attribs.centered = newattribs.centered;
|
||||
curMode.attribs.display = std::max(SDL_GetWindowDisplayIndex(window), 0);
|
||||
curMode.settings.resizable = (wflags & SDL_WINDOW_RESIZABLE) != 0;
|
||||
curMode.settings.borderless = (wflags & SDL_WINDOW_BORDERLESS) != 0;
|
||||
curMode.settings.centered = newsettings.centered;
|
||||
curMode.settings.display = std::max(SDL_GetWindowDisplayIndex(window), 0);
|
||||
|
||||
#if SDL_VERSION_ATLEAST(2,0,1)
|
||||
curMode.settings.highdpi = (wflags & SDL_WINDOW_ALLOW_HIGHDPI) != 0;
|
||||
#else
|
||||
curMode.settings.highdpi = false;
|
||||
#endif
|
||||
|
||||
// Only minimize on focus loss if the window is in exclusive-fullscreen
|
||||
// mode (mimics behaviour of SDL 2.0.2+).
|
||||
// In OS X we always disable this to prevent dock minimization weirdness.
|
||||
#ifndef LOVE_MACOSX
|
||||
if (curMode.attribs.fullscreen && curMode.attribs.fstype == FULLSCREEN_TYPE_NORMAL)
|
||||
if (curMode.settings.fullscreen && curMode.settings.fstype == FULLSCREEN_TYPE_NORMAL)
|
||||
SDL_SetHint(SDL_HINT_VIDEO_MINIMIZE_ON_FOCUS_LOSS, "1");
|
||||
else
|
||||
#endif
|
||||
@@ -351,15 +391,15 @@ void Window::displayError(const std::string &title, const std::string &text) con
|
||||
SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_ERROR, title.c_str(), text.c_str(), window);
|
||||
}
|
||||
|
||||
void Window::getWindow(int &width, int &height, WindowAttributes &attribs)
|
||||
void Window::getWindow(int &width, int &height, WindowSettings &settings)
|
||||
{
|
||||
// Window position may be different from creation - update display index.
|
||||
if (window)
|
||||
curMode.attribs.display = std::max(SDL_GetWindowDisplayIndex(window), 0);
|
||||
curMode.settings.display = std::max(SDL_GetWindowDisplayIndex(window), 0);
|
||||
|
||||
width = curMode.width;
|
||||
height = curMode.height;
|
||||
attribs = curMode.attribs;
|
||||
settings = curMode.settings;
|
||||
}
|
||||
|
||||
bool Window::setFullscreen(bool fullscreen, Window::FullscreenType fstype)
|
||||
@@ -367,9 +407,9 @@ bool Window::setFullscreen(bool fullscreen, Window::FullscreenType fstype)
|
||||
if (!window)
|
||||
return false;
|
||||
|
||||
WindowAttributes newattribs = curMode.attribs;
|
||||
newattribs.fullscreen = fullscreen;
|
||||
newattribs.fstype = fstype;
|
||||
WindowSettings newsettings = curMode.settings;
|
||||
newsettings.fullscreen = fullscreen;
|
||||
newsettings.fstype = fstype;
|
||||
|
||||
Uint32 sdlflags = 0;
|
||||
|
||||
@@ -393,12 +433,21 @@ bool Window::setFullscreen(bool fullscreen, Window::FullscreenType fstype)
|
||||
if (SDL_SetWindowFullscreen(window, sdlflags) == 0)
|
||||
{
|
||||
SDL_GL_MakeCurrent(window, context);
|
||||
updateAttributes(newattribs);
|
||||
updateSettings(newsettings);
|
||||
|
||||
// Update the viewport size now instead of waiting for event polling.
|
||||
graphics::Graphics *gfx = (graphics::Graphics *) Module::findInstance("love.graphics.");
|
||||
if (gfx)
|
||||
gfx->setViewportSize(curMode.width, curMode.height);
|
||||
if (gfx != nullptr)
|
||||
{
|
||||
int width = curMode.width;
|
||||
int height = curMode.height;
|
||||
|
||||
#if SDL_VERSION_ATLEAST(2,0,1)
|
||||
SDL_GL_GetDrawableSize(window, &width, &height);
|
||||
#endif
|
||||
|
||||
gfx->setViewportSize(width, height);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -408,7 +457,7 @@ bool Window::setFullscreen(bool fullscreen, Window::FullscreenType fstype)
|
||||
|
||||
bool Window::setFullscreen(bool fullscreen)
|
||||
{
|
||||
return setFullscreen(fullscreen, curMode.attribs.fstype);
|
||||
return setFullscreen(fullscreen, curMode.settings.fstype);
|
||||
}
|
||||
|
||||
int Window::getDisplayCount() const
|
||||
@@ -591,6 +640,26 @@ bool Window::isMouseGrabbed() const
|
||||
return mouseGrabbed;
|
||||
}
|
||||
|
||||
double Window::getPixelScale() const
|
||||
{
|
||||
double scale = 1.0;
|
||||
|
||||
#if SDL_VERSION_ATLEAST(2,0,1)
|
||||
if (window)
|
||||
{
|
||||
int wheight;
|
||||
SDL_GetWindowSize(window, nullptr, &wheight);
|
||||
|
||||
int dheight = wheight;
|
||||
SDL_GL_GetDrawableSize(window, nullptr, &dheight);
|
||||
|
||||
scale = (double) dheight / wheight;
|
||||
}
|
||||
#endif
|
||||
|
||||
return scale;
|
||||
}
|
||||
|
||||
const void *Window::getHandle() const
|
||||
{
|
||||
return window;
|
||||
|
||||
@@ -41,8 +41,8 @@ public:
|
||||
Window();
|
||||
~Window();
|
||||
|
||||
bool setWindow(int width = 800, int height = 600, WindowAttributes *attribs = 0);
|
||||
void getWindow(int &width, int &height, WindowAttributes &attribs);
|
||||
bool setWindow(int width = 800, int height = 600, WindowSettings *settings = nullptr);
|
||||
void getWindow(int &width, int &height, WindowSettings &settings);
|
||||
|
||||
bool setFullscreen(bool fullscreen, FullscreenType fstype);
|
||||
bool setFullscreen(bool fullscreen);
|
||||
@@ -79,6 +79,8 @@ public:
|
||||
void setMouseGrab(bool grab);
|
||||
bool isMouseGrabbed() const;
|
||||
|
||||
double getPixelScale() const;
|
||||
|
||||
const void *getHandle() const;
|
||||
|
||||
static love::window::Window *createSingleton();
|
||||
@@ -91,8 +93,8 @@ private:
|
||||
bool setContext(int fsaa, bool vsync);
|
||||
void setWindowGLAttributes(int fsaa) const;
|
||||
|
||||
// Update the saved window attribs based on the window's actual state.
|
||||
void updateAttributes(const WindowAttributes &newattribs);
|
||||
// Update the saved window settings based on the window's actual state.
|
||||
void updateSettings(const WindowSettings &newsettings);
|
||||
|
||||
// Shows a warning/error message box.
|
||||
void displayError(const std::string &title, const std::string &text) const;
|
||||
@@ -105,7 +107,7 @@ private:
|
||||
|
||||
int width;
|
||||
int height;
|
||||
WindowAttributes attribs;
|
||||
WindowSettings settings;
|
||||
love::image::ImageData *icon;
|
||||
|
||||
} curMode;
|
||||
|
||||
@@ -26,7 +26,7 @@ namespace love
|
||||
namespace window
|
||||
{
|
||||
|
||||
static Window *instance = 0;
|
||||
static Window *instance = nullptr;
|
||||
|
||||
int w_getDisplayCount(lua_State *L)
|
||||
{
|
||||
@@ -34,10 +34,10 @@ int w_getDisplayCount(lua_State *L)
|
||||
return 1;
|
||||
}
|
||||
|
||||
static const char *attribName(Window::Attribute attrib)
|
||||
static const char *settingName(Window::Setting setting)
|
||||
{
|
||||
const char *name = nullptr;
|
||||
Window::getConstant(attrib, name);
|
||||
Window::getConstant(setting, name);
|
||||
return name;
|
||||
}
|
||||
|
||||
@@ -62,91 +62,94 @@ int w_setMode(lua_State *L)
|
||||
return luax_typerror(L, -2, "string");
|
||||
|
||||
const char *key = luaL_checkstring(L, -2);
|
||||
Window::Attribute attrib;
|
||||
Window::Setting setting;
|
||||
|
||||
if (!Window::getConstant(key, attrib))
|
||||
return luaL_error(L, "Invalid window attribute: %s", key);
|
||||
if (!Window::getConstant(key, setting))
|
||||
return luaL_error(L, "Invalid window setting: %s", key);
|
||||
|
||||
lua_pop(L, 1);
|
||||
}
|
||||
|
||||
WindowAttributes attribs;
|
||||
WindowSettings settings;
|
||||
|
||||
lua_getfield(L, 3, attribName(Window::ATTRIB_FULLSCREEN_TYPE));
|
||||
lua_getfield(L, 3, settingName(Window::SETTING_FULLSCREEN_TYPE));
|
||||
if (!lua_isnoneornil(L, -1))
|
||||
{
|
||||
const char *typestr = luaL_checkstring(L, -1);
|
||||
|
||||
if (!Window::getConstant(typestr, attribs.fstype))
|
||||
if (!Window::getConstant(typestr, settings.fstype))
|
||||
return luaL_error(L, "Invalid fullscreen type: %s", typestr);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Default to "normal" fullscreen.
|
||||
attribs.fstype = Window::FULLSCREEN_TYPE_NORMAL;
|
||||
settings.fstype = Window::FULLSCREEN_TYPE_NORMAL;
|
||||
}
|
||||
lua_pop(L, 1);
|
||||
|
||||
attribs.fullscreen = luax_boolflag(L, 3, attribName(Window::ATTRIB_FULLSCREEN), false);
|
||||
attribs.vsync = luax_boolflag(L, 3, attribName(Window::ATTRIB_VSYNC), true);
|
||||
attribs.fsaa = luax_intflag(L, 3, attribName(Window::ATTRIB_FSAA), 0);
|
||||
attribs.resizable = luax_boolflag(L, 3, attribName(Window::ATTRIB_RESIZABLE), false);
|
||||
attribs.minwidth = luax_intflag(L, 3, attribName(Window::ATTRIB_MIN_WIDTH), 1);
|
||||
attribs.minheight = luax_intflag(L, 3, attribName(Window::ATTRIB_MIN_HEIGHT), 1);
|
||||
attribs.borderless = luax_boolflag(L, 3, attribName(Window::ATTRIB_BORDERLESS), false);
|
||||
attribs.centered = luax_boolflag(L, 3, attribName(Window::ATTRIB_CENTERED), true);
|
||||
attribs.display = luax_intflag(L, 3, attribName(Window::ATTRIB_DISPLAY), 1);
|
||||
settings.fullscreen = luax_boolflag(L, 3, settingName(Window::SETTING_FULLSCREEN), false);
|
||||
settings.vsync = luax_boolflag(L, 3, settingName(Window::SETTING_VSYNC), true);
|
||||
settings.fsaa = luax_intflag(L, 3, settingName(Window::SETTING_FSAA), 0);
|
||||
settings.resizable = luax_boolflag(L, 3, settingName(Window::SETTING_RESIZABLE), false);
|
||||
settings.minwidth = luax_intflag(L, 3, settingName(Window::SETTING_MIN_WIDTH), 1);
|
||||
settings.minheight = luax_intflag(L, 3, settingName(Window::SETTING_MIN_HEIGHT), 1);
|
||||
settings.borderless = luax_boolflag(L, 3, settingName(Window::SETTING_BORDERLESS), false);
|
||||
settings.centered = luax_boolflag(L, 3, settingName(Window::SETTING_CENTERED), true);
|
||||
settings.display = luax_intflag(L, 3, settingName(Window::SETTING_DISPLAY), 1);
|
||||
settings.highdpi = luax_boolflag(L, 3, settingName(Window::SETTING_HIGHDPI), false);
|
||||
|
||||
// Display index is 1-based in Lua and 0-based internally.
|
||||
attribs.display--;
|
||||
settings.display--;
|
||||
|
||||
EXCEPT_GUARD(luax_pushboolean(L, instance->setWindow(w, h, &attribs));)
|
||||
EXCEPT_GUARD(luax_pushboolean(L, instance->setWindow(w, h, &settings));)
|
||||
return 1;
|
||||
}
|
||||
|
||||
int w_getMode(lua_State *L)
|
||||
{
|
||||
int w, h;
|
||||
WindowAttributes attribs;
|
||||
instance->getWindow(w, h, attribs);
|
||||
WindowSettings settings;
|
||||
instance->getWindow(w, h, settings);
|
||||
lua_pushnumber(L, w);
|
||||
lua_pushnumber(L, h);
|
||||
|
||||
lua_newtable(L);
|
||||
|
||||
const char *fstypestr = "normal";
|
||||
Window::getConstant(attribs.fstype, fstypestr);
|
||||
Window::getConstant(settings.fstype, fstypestr);
|
||||
|
||||
lua_pushstring(L, fstypestr);
|
||||
lua_setfield(L, -2, attribName(Window::ATTRIB_FULLSCREEN_TYPE));
|
||||
lua_setfield(L, -2, settingName(Window::SETTING_FULLSCREEN_TYPE));
|
||||
|
||||
luax_pushboolean(L, attribs.fullscreen);
|
||||
lua_setfield(L, -2, attribName(Window::ATTRIB_FULLSCREEN));
|
||||
luax_pushboolean(L, settings.fullscreen);
|
||||
lua_setfield(L, -2, settingName(Window::SETTING_FULLSCREEN));
|
||||
|
||||
luax_pushboolean(L, attribs.vsync);
|
||||
lua_setfield(L, -2, attribName(Window::ATTRIB_VSYNC));
|
||||
luax_pushboolean(L, settings.vsync);
|
||||
lua_setfield(L, -2, settingName(Window::SETTING_VSYNC));
|
||||
|
||||
lua_pushinteger(L, attribs.fsaa);
|
||||
lua_setfield(L, -2, attribName(Window::ATTRIB_FSAA));
|
||||
lua_pushinteger(L, settings.fsaa);
|
||||
lua_setfield(L, -2, settingName(Window::SETTING_FSAA));
|
||||
|
||||
luax_pushboolean(L, attribs.resizable);
|
||||
lua_setfield(L, -2, attribName(Window::ATTRIB_RESIZABLE));
|
||||
luax_pushboolean(L, settings.resizable);
|
||||
lua_setfield(L, -2, settingName(Window::SETTING_RESIZABLE));
|
||||
|
||||
lua_pushinteger(L, attribs.minwidth);
|
||||
lua_setfield(L, -2, attribName(Window::ATTRIB_MIN_WIDTH));
|
||||
lua_pushinteger(L, settings.minwidth);
|
||||
lua_setfield(L, -2, settingName(Window::SETTING_MIN_WIDTH));
|
||||
|
||||
lua_pushinteger(L, attribs.minheight);
|
||||
lua_setfield(L, -2, attribName(Window::ATTRIB_MIN_HEIGHT));
|
||||
lua_pushinteger(L, settings.minheight);
|
||||
lua_setfield(L, -2, settingName(Window::SETTING_MIN_HEIGHT));
|
||||
|
||||
luax_pushboolean(L, attribs.borderless);
|
||||
lua_setfield(L, -2, attribName(Window::ATTRIB_BORDERLESS));
|
||||
luax_pushboolean(L, settings.borderless);
|
||||
lua_setfield(L, -2, settingName(Window::SETTING_BORDERLESS));
|
||||
|
||||
luax_pushboolean(L, attribs.centered);
|
||||
lua_setfield(L, -2, attribName(Window::ATTRIB_CENTERED));
|
||||
luax_pushboolean(L, settings.centered);
|
||||
lua_setfield(L, -2, settingName(Window::SETTING_CENTERED));
|
||||
|
||||
// Display index is 0-based internally and 1-based in Lua.
|
||||
lua_pushinteger(L, attribs.display + 1);
|
||||
lua_setfield(L, -2, attribName(Window::ATTRIB_DISPLAY));
|
||||
lua_pushinteger(L, settings.display + 1);
|
||||
lua_setfield(L, -2, settingName(Window::SETTING_DISPLAY));
|
||||
|
||||
luax_pushboolean(L, settings.highdpi);
|
||||
lua_setfield(L, -2, settingName(Window::SETTING_HIGHDPI));
|
||||
|
||||
return 3;
|
||||
}
|
||||
@@ -202,14 +205,14 @@ int w_setFullscreen(lua_State *L)
|
||||
int w_getFullscreen(lua_State *L)
|
||||
{
|
||||
int w, h;
|
||||
WindowAttributes attribs;
|
||||
instance->getWindow(w, h, attribs);
|
||||
WindowSettings settings;
|
||||
instance->getWindow(w, h, settings);
|
||||
|
||||
const char *typestr;
|
||||
if (!Window::getConstant(attribs.fstype, typestr))
|
||||
if (!Window::getConstant(settings.fstype, typestr))
|
||||
luaL_error(L, "Unknown fullscreen type.");
|
||||
|
||||
luax_pushboolean(L, attribs.fullscreen);
|
||||
luax_pushboolean(L, settings.fullscreen);
|
||||
lua_pushstring(L, typestr);
|
||||
return 2;
|
||||
}
|
||||
@@ -300,6 +303,12 @@ int w_isVisible(lua_State *L)
|
||||
return 1;
|
||||
}
|
||||
|
||||
int w_getPixelScale(lua_State *L)
|
||||
{
|
||||
lua_pushnumber(L, instance->getPixelScale());
|
||||
return 1;
|
||||
}
|
||||
|
||||
static const luaL_Reg functions[] =
|
||||
{
|
||||
{ "getDisplayCount", w_getDisplayCount },
|
||||
@@ -320,6 +329,7 @@ static const luaL_Reg functions[] =
|
||||
{ "hasFocus", w_hasFocus },
|
||||
{ "hasMouseFocus", w_hasMouseFocus },
|
||||
{ "isVisible", w_isVisible },
|
||||
{ "getPixelScale", w_getPixelScale },
|
||||
{ 0, 0 }
|
||||
};
|
||||
|
||||
|
||||
@@ -47,6 +47,7 @@ int w_getTitle(lua_State *L);
|
||||
int w_hasFocus(lua_State *L);
|
||||
int w_hasMouseFocus(lua_State *L);
|
||||
int w_isVisible(lua_State *L);
|
||||
int w_getPixelScale(lua_State *L);
|
||||
extern "C" LOVE_EXPORT int luaopen_love_window(lua_State *L);
|
||||
|
||||
} // window
|
||||
|
||||
@@ -164,20 +164,20 @@ function love.createhandlers()
|
||||
textedit = function (t,s,l)
|
||||
if love.textedit then return love.textedit(t,s,l) end
|
||||
end,
|
||||
mousepressed = function (x,y,b)
|
||||
if love.mousepressed then return love.mousepressed(x,y,b) end
|
||||
mousepressed = function (x,y,b,t)
|
||||
if love.mousepressed then return love.mousepressed(x,y,b,t) end
|
||||
end,
|
||||
mousereleased = function (x,y,b)
|
||||
if love.mousereleased then return love.mousereleased(x,y,b) end
|
||||
mousereleased = function (x,y,b,t)
|
||||
if love.mousereleased then return love.mousereleased(x,y,b,t) end
|
||||
end,
|
||||
fingerpressed = function (x,y,b)
|
||||
if love.fingerpressed then return love.fingerpressed(x,y,b) end
|
||||
touchpressed = function (id,x,y,p)
|
||||
if love.touchpressed then return love.touchpressed(id,x,y,p) end
|
||||
end,
|
||||
fingerreleased = function (x,y,b)
|
||||
if love.fingerreleased then return love.fingerreleased(x,y,b) end
|
||||
touchreleased = function (id,x,y,p)
|
||||
if love.touchreleased then return love.touchreleased(id,x,y,p) end
|
||||
end,
|
||||
fingermotion = function (x,y,b)
|
||||
if love.fingermotion then return love.fingermotion(x,y,b) end
|
||||
touchmoved = function (id,x,y,p)
|
||||
if love.touchmoved then return love.touchmoved(id,x,y,p) end
|
||||
end,
|
||||
joystickpressed = function (j,b)
|
||||
if love.joystickpressed then return love.joystickpressed(j,b) end
|
||||
@@ -309,6 +309,7 @@ function love.init()
|
||||
borderless = false,
|
||||
resizable = false,
|
||||
centered = true,
|
||||
highdpi = false,
|
||||
},
|
||||
modules = {
|
||||
event = true,
|
||||
@@ -325,6 +326,7 @@ function love.init()
|
||||
system = true,
|
||||
font = true,
|
||||
thread = true,
|
||||
touch = true,
|
||||
window = true,
|
||||
},
|
||||
console = false, -- Only relevant for windows.
|
||||
@@ -359,6 +361,7 @@ function love.init()
|
||||
"keyboard",
|
||||
"joystick",
|
||||
"mouse",
|
||||
"touch",
|
||||
"sound",
|
||||
"system",
|
||||
"audio",
|
||||
@@ -397,6 +400,7 @@ function love.init()
|
||||
borderless = c.window.borderless,
|
||||
centered = c.window.centered,
|
||||
display = c.window.display,
|
||||
highdpi = c.window.highdpi,
|
||||
}), "Could not set window mode")
|
||||
love.window.setTitle(c.window.title or c.title)
|
||||
if c.window.icon then
|
||||
@@ -482,8 +486,8 @@ function love.run()
|
||||
-- Process events.
|
||||
if love.event then
|
||||
love.event.pump()
|
||||
for e,a,b,c,d in love.event.poll() do
|
||||
if e == "quit" then
|
||||
for n,a,b,c,d in love.event.poll() do
|
||||
if n == "quit" then
|
||||
if not love.quit or not love.quit() then
|
||||
if love.audio then
|
||||
love.audio.stop()
|
||||
@@ -491,7 +495,7 @@ function love.run()
|
||||
return
|
||||
end
|
||||
end
|
||||
love.handlers[e](a,b,c,d)
|
||||
love.handlers[n](a,b,c,d)
|
||||
end
|
||||
end
|
||||
|
||||
@@ -1382,8 +1386,9 @@ function love.nogame()
|
||||
local ox = rain.ox
|
||||
local oy = rain.oy
|
||||
|
||||
local batch_w = 2 * math.ceil(love.graphics.getWidth() / sx) + 2
|
||||
local batch_h = 2 * math.ceil(love.graphics.getHeight() / sy) + 2
|
||||
local m = 1 / love.window.getPixelScale()
|
||||
local batch_w = 2 * math.ceil(m * love.graphics.getWidth() / sx) + 2
|
||||
local batch_h = 2 * math.ceil(m * love.graphics.getHeight() / sy) + 2
|
||||
|
||||
batch:clear()
|
||||
|
||||
@@ -1418,8 +1423,9 @@ function love.nogame()
|
||||
g_time = g_time + dt / 2
|
||||
local int, frac = math.modf(g_time)
|
||||
update_rain(frac)
|
||||
inspector.x = love.graphics.getWidth() * 0.45
|
||||
inspector.y = love.graphics.getHeight() * 0.55
|
||||
local scale = love.window.getPixelScale()
|
||||
inspector.x = love.graphics.getWidth() * 0.45 / scale
|
||||
inspector.y = love.graphics.getHeight() * 0.55 / scale
|
||||
end
|
||||
|
||||
local function draw_grid()
|
||||
@@ -1490,8 +1496,13 @@ function love.nogame()
|
||||
function love.draw()
|
||||
love.graphics.setColor(255, 255, 255)
|
||||
|
||||
love.graphics.push()
|
||||
love.graphics.scale(love.window.getPixelScale())
|
||||
|
||||
draw_grid()
|
||||
draw_inspector()
|
||||
|
||||
love.graphics.pop()
|
||||
end
|
||||
|
||||
function love.keyreleased(key)
|
||||
@@ -1507,6 +1518,7 @@ function love.nogame()
|
||||
t.modules.physics = false
|
||||
t.modules.joystick = false
|
||||
t.window.resizable = true
|
||||
t.window.highdpi = true
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
@@ -284,39 +284,40 @@ const unsigned char boot_lua[] =
|
||||
0x6e, 0x64, 0x0a,
|
||||
0x09, 0x09, 0x65, 0x6e, 0x64, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x70, 0x72, 0x65, 0x73, 0x73, 0x65, 0x64, 0x20, 0x3d, 0x20, 0x66,
|
||||
0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x28, 0x78, 0x2c, 0x79, 0x2c, 0x62, 0x29, 0x0a,
|
||||
0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x28, 0x78, 0x2c, 0x79, 0x2c, 0x62, 0x2c, 0x74, 0x29, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x69, 0x66, 0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x70, 0x72,
|
||||
0x65, 0x73, 0x73, 0x65, 0x64, 0x20, 0x74, 0x68, 0x65, 0x6e, 0x20, 0x72, 0x65, 0x74, 0x75, 0x72, 0x6e, 0x20,
|
||||
0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x70, 0x72, 0x65, 0x73, 0x73, 0x65, 0x64, 0x28,
|
||||
0x78, 0x2c, 0x79, 0x2c, 0x62, 0x29, 0x20, 0x65, 0x6e, 0x64, 0x0a,
|
||||
0x78, 0x2c, 0x79, 0x2c, 0x62, 0x2c, 0x74, 0x29, 0x20, 0x65, 0x6e, 0x64, 0x0a,
|
||||
0x09, 0x09, 0x65, 0x6e, 0x64, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x72, 0x65, 0x6c, 0x65, 0x61, 0x73, 0x65, 0x64, 0x20, 0x3d, 0x20,
|
||||
0x66, 0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x28, 0x78, 0x2c, 0x79, 0x2c, 0x62, 0x29, 0x0a,
|
||||
0x66, 0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x28, 0x78, 0x2c, 0x79, 0x2c, 0x62, 0x2c, 0x74, 0x29, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x69, 0x66, 0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x72, 0x65,
|
||||
0x6c, 0x65, 0x61, 0x73, 0x65, 0x64, 0x20, 0x74, 0x68, 0x65, 0x6e, 0x20, 0x72, 0x65, 0x74, 0x75, 0x72, 0x6e,
|
||||
0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x72, 0x65, 0x6c, 0x65, 0x61, 0x73, 0x65,
|
||||
0x64, 0x28, 0x78, 0x2c, 0x79, 0x2c, 0x62, 0x29, 0x20, 0x65, 0x6e, 0x64, 0x0a,
|
||||
0x64, 0x28, 0x78, 0x2c, 0x79, 0x2c, 0x62, 0x2c, 0x74, 0x29, 0x20, 0x65, 0x6e, 0x64, 0x0a,
|
||||
0x09, 0x09, 0x65, 0x6e, 0x64, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x66, 0x69, 0x6e, 0x67, 0x65, 0x72, 0x70, 0x72, 0x65, 0x73, 0x73, 0x65, 0x64, 0x20, 0x3d, 0x20,
|
||||
0x66, 0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x28, 0x78, 0x2c, 0x79, 0x2c, 0x62, 0x29, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x69, 0x66, 0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x66, 0x69, 0x6e, 0x67, 0x65, 0x72, 0x70,
|
||||
0x72, 0x65, 0x73, 0x73, 0x65, 0x64, 0x20, 0x74, 0x68, 0x65, 0x6e, 0x20, 0x72, 0x65, 0x74, 0x75, 0x72, 0x6e,
|
||||
0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x66, 0x69, 0x6e, 0x67, 0x65, 0x72, 0x70, 0x72, 0x65, 0x73, 0x73, 0x65,
|
||||
0x64, 0x28, 0x78, 0x2c, 0x79, 0x2c, 0x62, 0x29, 0x20, 0x65, 0x6e, 0x64, 0x0a,
|
||||
0x09, 0x09, 0x74, 0x6f, 0x75, 0x63, 0x68, 0x70, 0x72, 0x65, 0x73, 0x73, 0x65, 0x64, 0x20, 0x3d, 0x20, 0x66,
|
||||
0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x28, 0x69, 0x64, 0x2c, 0x78, 0x2c, 0x79, 0x2c, 0x70, 0x29, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x69, 0x66, 0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x74, 0x6f, 0x75, 0x63, 0x68, 0x70, 0x72,
|
||||
0x65, 0x73, 0x73, 0x65, 0x64, 0x20, 0x74, 0x68, 0x65, 0x6e, 0x20, 0x72, 0x65, 0x74, 0x75, 0x72, 0x6e, 0x20,
|
||||
0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x74, 0x6f, 0x75, 0x63, 0x68, 0x70, 0x72, 0x65, 0x73, 0x73, 0x65, 0x64, 0x28,
|
||||
0x69, 0x64, 0x2c, 0x78, 0x2c, 0x79, 0x2c, 0x70, 0x29, 0x20, 0x65, 0x6e, 0x64, 0x0a,
|
||||
0x09, 0x09, 0x65, 0x6e, 0x64, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x66, 0x69, 0x6e, 0x67, 0x65, 0x72, 0x72, 0x65, 0x6c, 0x65, 0x61, 0x73, 0x65, 0x64, 0x20, 0x3d,
|
||||
0x20, 0x66, 0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x28, 0x78, 0x2c, 0x79, 0x2c, 0x62, 0x29, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x69, 0x66, 0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x66, 0x69, 0x6e, 0x67, 0x65, 0x72, 0x72,
|
||||
0x65, 0x6c, 0x65, 0x61, 0x73, 0x65, 0x64, 0x20, 0x74, 0x68, 0x65, 0x6e, 0x20, 0x72, 0x65, 0x74, 0x75, 0x72,
|
||||
0x6e, 0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x66, 0x69, 0x6e, 0x67, 0x65, 0x72, 0x72, 0x65, 0x6c, 0x65, 0x61,
|
||||
0x73, 0x65, 0x64, 0x28, 0x78, 0x2c, 0x79, 0x2c, 0x62, 0x29, 0x20, 0x65, 0x6e, 0x64, 0x0a,
|
||||
0x09, 0x09, 0x74, 0x6f, 0x75, 0x63, 0x68, 0x72, 0x65, 0x6c, 0x65, 0x61, 0x73, 0x65, 0x64, 0x20, 0x3d, 0x20,
|
||||
0x66, 0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x28, 0x69, 0x64, 0x2c, 0x78, 0x2c, 0x79, 0x2c, 0x70,
|
||||
0x29, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x69, 0x66, 0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x74, 0x6f, 0x75, 0x63, 0x68, 0x72, 0x65,
|
||||
0x6c, 0x65, 0x61, 0x73, 0x65, 0x64, 0x20, 0x74, 0x68, 0x65, 0x6e, 0x20, 0x72, 0x65, 0x74, 0x75, 0x72, 0x6e,
|
||||
0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x74, 0x6f, 0x75, 0x63, 0x68, 0x72, 0x65, 0x6c, 0x65, 0x61, 0x73, 0x65,
|
||||
0x64, 0x28, 0x69, 0x64, 0x2c, 0x78, 0x2c, 0x79, 0x2c, 0x70, 0x29, 0x20, 0x65, 0x6e, 0x64, 0x0a,
|
||||
0x09, 0x09, 0x65, 0x6e, 0x64, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x66, 0x69, 0x6e, 0x67, 0x65, 0x72, 0x6d, 0x6f, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x3d, 0x20, 0x66,
|
||||
0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x28, 0x78, 0x2c, 0x79, 0x2c, 0x62, 0x29, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x69, 0x66, 0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x66, 0x69, 0x6e, 0x67, 0x65, 0x72, 0x6d,
|
||||
0x6f, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x74, 0x68, 0x65, 0x6e, 0x20, 0x72, 0x65, 0x74, 0x75, 0x72, 0x6e, 0x20,
|
||||
0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x66, 0x69, 0x6e, 0x67, 0x65, 0x72, 0x6d, 0x6f, 0x74, 0x69, 0x6f, 0x6e, 0x28,
|
||||
0x78, 0x2c, 0x79, 0x2c, 0x62, 0x29, 0x20, 0x65, 0x6e, 0x64, 0x0a,
|
||||
0x09, 0x09, 0x74, 0x6f, 0x75, 0x63, 0x68, 0x6d, 0x6f, 0x76, 0x65, 0x64, 0x20, 0x3d, 0x20, 0x66, 0x75, 0x6e,
|
||||
0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x28, 0x69, 0x64, 0x2c, 0x78, 0x2c, 0x79, 0x2c, 0x70, 0x29, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x69, 0x66, 0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x74, 0x6f, 0x75, 0x63, 0x68, 0x6d, 0x6f,
|
||||
0x76, 0x65, 0x64, 0x20, 0x74, 0x68, 0x65, 0x6e, 0x20, 0x72, 0x65, 0x74, 0x75, 0x72, 0x6e, 0x20, 0x6c, 0x6f,
|
||||
0x76, 0x65, 0x2e, 0x74, 0x6f, 0x75, 0x63, 0x68, 0x6d, 0x6f, 0x76, 0x65, 0x64, 0x28, 0x69, 0x64, 0x2c, 0x78,
|
||||
0x2c, 0x79, 0x2c, 0x70, 0x29, 0x20, 0x65, 0x6e, 0x64, 0x0a,
|
||||
0x09, 0x09, 0x65, 0x6e, 0x64, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x6a, 0x6f, 0x79, 0x73, 0x74, 0x69, 0x63, 0x6b, 0x70, 0x72, 0x65, 0x73, 0x73, 0x65, 0x64, 0x20,
|
||||
0x3d, 0x20, 0x66, 0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x28, 0x6a, 0x2c, 0x62, 0x29, 0x0a,
|
||||
@@ -558,6 +559,8 @@ const unsigned char boot_lua[] =
|
||||
0x73, 0x65, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x63, 0x65, 0x6e, 0x74, 0x65, 0x72, 0x65, 0x64, 0x20, 0x3d, 0x20, 0x74, 0x72, 0x75, 0x65,
|
||||
0x2c, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x68, 0x69, 0x67, 0x68, 0x64, 0x70, 0x69, 0x20, 0x3d, 0x20, 0x66, 0x61, 0x6c, 0x73, 0x65,
|
||||
0x2c, 0x0a,
|
||||
0x09, 0x09, 0x7d, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x6d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x73, 0x20, 0x3d, 0x20, 0x7b, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x65, 0x76, 0x65, 0x6e, 0x74, 0x20, 0x3d, 0x20, 0x74, 0x72, 0x75, 0x65, 0x2c, 0x0a,
|
||||
@@ -577,6 +580,7 @@ const unsigned char boot_lua[] =
|
||||
0x09, 0x09, 0x09, 0x73, 0x79, 0x73, 0x74, 0x65, 0x6d, 0x20, 0x3d, 0x20, 0x74, 0x72, 0x75, 0x65, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x66, 0x6f, 0x6e, 0x74, 0x20, 0x3d, 0x20, 0x74, 0x72, 0x75, 0x65, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x74, 0x68, 0x72, 0x65, 0x61, 0x64, 0x20, 0x3d, 0x20, 0x74, 0x72, 0x75, 0x65, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x74, 0x6f, 0x75, 0x63, 0x68, 0x20, 0x3d, 0x20, 0x74, 0x72, 0x75, 0x65, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x77, 0x69, 0x6e, 0x64, 0x6f, 0x77, 0x20, 0x3d, 0x20, 0x74, 0x72, 0x75, 0x65, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x7d, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x63, 0x6f, 0x6e, 0x73, 0x6f, 0x6c, 0x65, 0x20, 0x3d, 0x20, 0x66, 0x61, 0x6c, 0x73, 0x65, 0x2c,
|
||||
@@ -630,6 +634,7 @@ const unsigned char boot_lua[] =
|
||||
0x09, 0x09, 0x22, 0x6b, 0x65, 0x79, 0x62, 0x6f, 0x61, 0x72, 0x64, 0x22, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x22, 0x6a, 0x6f, 0x79, 0x73, 0x74, 0x69, 0x63, 0x6b, 0x22, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x22, 0x6d, 0x6f, 0x75, 0x73, 0x65, 0x22, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x22, 0x74, 0x6f, 0x75, 0x63, 0x68, 0x22, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x22, 0x73, 0x6f, 0x75, 0x6e, 0x64, 0x22, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x22, 0x73, 0x79, 0x73, 0x74, 0x65, 0x6d, 0x22, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x22, 0x61, 0x75, 0x64, 0x69, 0x6f, 0x22, 0x2c, 0x0a,
|
||||
@@ -689,6 +694,8 @@ const unsigned char boot_lua[] =
|
||||
0x6e, 0x64, 0x6f, 0x77, 0x2e, 0x63, 0x65, 0x6e, 0x74, 0x65, 0x72, 0x65, 0x64, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x64, 0x69, 0x73, 0x70, 0x6c, 0x61, 0x79, 0x20, 0x3d, 0x20, 0x63, 0x2e, 0x77, 0x69, 0x6e,
|
||||
0x64, 0x6f, 0x77, 0x2e, 0x64, 0x69, 0x73, 0x70, 0x6c, 0x61, 0x79, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x68, 0x69, 0x67, 0x68, 0x64, 0x70, 0x69, 0x20, 0x3d, 0x20, 0x63, 0x2e, 0x77, 0x69, 0x6e,
|
||||
0x64, 0x6f, 0x77, 0x2e, 0x68, 0x69, 0x67, 0x68, 0x64, 0x70, 0x69, 0x2c, 0x0a,
|
||||
0x09, 0x09, 0x7d, 0x29, 0x2c, 0x20, 0x22, 0x43, 0x6f, 0x75, 0x6c, 0x64, 0x20, 0x6e, 0x6f, 0x74, 0x20, 0x73,
|
||||
0x65, 0x74, 0x20, 0x77, 0x69, 0x6e, 0x64, 0x6f, 0x77, 0x20, 0x6d, 0x6f, 0x64, 0x65, 0x22, 0x29, 0x0a,
|
||||
0x09, 0x09, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x77, 0x69, 0x6e, 0x64, 0x6f, 0x77, 0x2e, 0x73, 0x65, 0x74, 0x54,
|
||||
@@ -854,10 +861,10 @@ const unsigned char boot_lua[] =
|
||||
0x65, 0x6e, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x65, 0x76, 0x65, 0x6e, 0x74, 0x2e, 0x70, 0x75, 0x6d, 0x70,
|
||||
0x28, 0x29, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x66, 0x6f, 0x72, 0x20, 0x65, 0x2c, 0x61, 0x2c, 0x62, 0x2c, 0x63, 0x2c, 0x64, 0x20, 0x69,
|
||||
0x09, 0x09, 0x09, 0x66, 0x6f, 0x72, 0x20, 0x6e, 0x2c, 0x61, 0x2c, 0x62, 0x2c, 0x63, 0x2c, 0x64, 0x20, 0x69,
|
||||
0x6e, 0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x65, 0x76, 0x65, 0x6e, 0x74, 0x2e, 0x70, 0x6f, 0x6c, 0x6c, 0x28,
|
||||
0x29, 0x20, 0x64, 0x6f, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x09, 0x69, 0x66, 0x20, 0x65, 0x20, 0x3d, 0x3d, 0x20, 0x22, 0x71, 0x75, 0x69, 0x74, 0x22,
|
||||
0x09, 0x09, 0x09, 0x09, 0x69, 0x66, 0x20, 0x6e, 0x20, 0x3d, 0x3d, 0x20, 0x22, 0x71, 0x75, 0x69, 0x74, 0x22,
|
||||
0x20, 0x74, 0x68, 0x65, 0x6e, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x09, 0x09, 0x69, 0x66, 0x20, 0x6e, 0x6f, 0x74, 0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x71,
|
||||
0x75, 0x69, 0x74, 0x20, 0x6f, 0x72, 0x20, 0x6e, 0x6f, 0x74, 0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x71, 0x75,
|
||||
@@ -871,7 +878,7 @@ const unsigned char boot_lua[] =
|
||||
0x09, 0x09, 0x09, 0x09, 0x09, 0x65, 0x6e, 0x64, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x09, 0x65, 0x6e, 0x64, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x09, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x68, 0x61, 0x6e, 0x64, 0x6c, 0x65, 0x72, 0x73, 0x5b,
|
||||
0x65, 0x5d, 0x28, 0x61, 0x2c, 0x62, 0x2c, 0x63, 0x2c, 0x64, 0x29, 0x0a,
|
||||
0x6e, 0x5d, 0x28, 0x61, 0x2c, 0x62, 0x2c, 0x63, 0x2c, 0x64, 0x29, 0x0a,
|
||||
0x09, 0x09, 0x09, 0x65, 0x6e, 0x64, 0x0a,
|
||||
0x09, 0x09, 0x65, 0x6e, 0x64, 0x0a,
|
||||
0x09, 0x09, 0x2d, 0x2d, 0x20, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x20, 0x64, 0x74, 0x2c, 0x20, 0x61, 0x73,
|
||||
@@ -4945,14 +4952,17 @@ const unsigned char boot_lua[] =
|
||||
0x6f, 0x78, 0x0a,
|
||||
0x09, 0x09, 0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x20, 0x6f, 0x79, 0x20, 0x3d, 0x20, 0x72, 0x61, 0x69, 0x6e, 0x2e,
|
||||
0x6f, 0x79, 0x0a,
|
||||
0x09, 0x09, 0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x20, 0x6d, 0x20, 0x3d, 0x20, 0x31, 0x20, 0x2f, 0x20, 0x6c, 0x6f,
|
||||
0x76, 0x65, 0x2e, 0x77, 0x69, 0x6e, 0x64, 0x6f, 0x77, 0x2e, 0x67, 0x65, 0x74, 0x50, 0x69, 0x78, 0x65, 0x6c,
|
||||
0x53, 0x63, 0x61, 0x6c, 0x65, 0x28, 0x29, 0x0a,
|
||||
0x09, 0x09, 0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x20, 0x62, 0x61, 0x74, 0x63, 0x68, 0x5f, 0x77, 0x20, 0x3d, 0x20,
|
||||
0x32, 0x20, 0x2a, 0x20, 0x6d, 0x61, 0x74, 0x68, 0x2e, 0x63, 0x65, 0x69, 0x6c, 0x28, 0x6c, 0x6f, 0x76, 0x65,
|
||||
0x2e, 0x67, 0x72, 0x61, 0x70, 0x68, 0x69, 0x63, 0x73, 0x2e, 0x67, 0x65, 0x74, 0x57, 0x69, 0x64, 0x74, 0x68,
|
||||
0x28, 0x29, 0x20, 0x2f, 0x20, 0x73, 0x78, 0x29, 0x20, 0x2b, 0x20, 0x32, 0x0a,
|
||||
0x32, 0x20, 0x2a, 0x20, 0x6d, 0x61, 0x74, 0x68, 0x2e, 0x63, 0x65, 0x69, 0x6c, 0x28, 0x6d, 0x20, 0x2a, 0x20,
|
||||
0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x67, 0x72, 0x61, 0x70, 0x68, 0x69, 0x63, 0x73, 0x2e, 0x67, 0x65, 0x74, 0x57,
|
||||
0x69, 0x64, 0x74, 0x68, 0x28, 0x29, 0x20, 0x2f, 0x20, 0x73, 0x78, 0x29, 0x20, 0x2b, 0x20, 0x32, 0x0a,
|
||||
0x09, 0x09, 0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x20, 0x62, 0x61, 0x74, 0x63, 0x68, 0x5f, 0x68, 0x20, 0x3d, 0x20,
|
||||
0x32, 0x20, 0x2a, 0x20, 0x6d, 0x61, 0x74, 0x68, 0x2e, 0x63, 0x65, 0x69, 0x6c, 0x28, 0x6c, 0x6f, 0x76, 0x65,
|
||||
0x2e, 0x67, 0x72, 0x61, 0x70, 0x68, 0x69, 0x63, 0x73, 0x2e, 0x67, 0x65, 0x74, 0x48, 0x65, 0x69, 0x67, 0x68,
|
||||
0x74, 0x28, 0x29, 0x20, 0x2f, 0x20, 0x73, 0x79, 0x29, 0x20, 0x2b, 0x20, 0x32, 0x0a,
|
||||
0x32, 0x20, 0x2a, 0x20, 0x6d, 0x61, 0x74, 0x68, 0x2e, 0x63, 0x65, 0x69, 0x6c, 0x28, 0x6d, 0x20, 0x2a, 0x20,
|
||||
0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x67, 0x72, 0x61, 0x70, 0x68, 0x69, 0x63, 0x73, 0x2e, 0x67, 0x65, 0x74, 0x48,
|
||||
0x65, 0x69, 0x67, 0x68, 0x74, 0x28, 0x29, 0x20, 0x2f, 0x20, 0x73, 0x79, 0x29, 0x20, 0x2b, 0x20, 0x32, 0x0a,
|
||||
0x09, 0x09, 0x62, 0x61, 0x74, 0x63, 0x68, 0x3a, 0x63, 0x6c, 0x65, 0x61, 0x72, 0x28, 0x29, 0x0a,
|
||||
0x09, 0x09, 0x69, 0x66, 0x20, 0x62, 0x61, 0x74, 0x63, 0x68, 0x3a, 0x67, 0x65, 0x74, 0x42, 0x75, 0x66, 0x66,
|
||||
0x65, 0x72, 0x53, 0x69, 0x7a, 0x65, 0x28, 0x29, 0x20, 0x3c, 0x20, 0x62, 0x61, 0x74, 0x63, 0x68, 0x5f, 0x77,
|
||||
@@ -4998,12 +5008,17 @@ const unsigned char boot_lua[] =
|
||||
0x29, 0x0a,
|
||||
0x09, 0x09, 0x75, 0x70, 0x64, 0x61, 0x74, 0x65, 0x5f, 0x72, 0x61, 0x69, 0x6e, 0x28, 0x66, 0x72, 0x61, 0x63,
|
||||
0x29, 0x0a,
|
||||
0x09, 0x09, 0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x20, 0x73, 0x63, 0x61, 0x6c, 0x65, 0x20, 0x3d, 0x20, 0x6c, 0x6f,
|
||||
0x76, 0x65, 0x2e, 0x77, 0x69, 0x6e, 0x64, 0x6f, 0x77, 0x2e, 0x67, 0x65, 0x74, 0x50, 0x69, 0x78, 0x65, 0x6c,
|
||||
0x53, 0x63, 0x61, 0x6c, 0x65, 0x28, 0x29, 0x0a,
|
||||
0x09, 0x09, 0x69, 0x6e, 0x73, 0x70, 0x65, 0x63, 0x74, 0x6f, 0x72, 0x2e, 0x78, 0x20, 0x3d, 0x20, 0x6c, 0x6f,
|
||||
0x76, 0x65, 0x2e, 0x67, 0x72, 0x61, 0x70, 0x68, 0x69, 0x63, 0x73, 0x2e, 0x67, 0x65, 0x74, 0x57, 0x69, 0x64,
|
||||
0x74, 0x68, 0x28, 0x29, 0x20, 0x2a, 0x20, 0x30, 0x2e, 0x34, 0x35, 0x0a,
|
||||
0x74, 0x68, 0x28, 0x29, 0x20, 0x2a, 0x20, 0x30, 0x2e, 0x34, 0x35, 0x20, 0x2f, 0x20, 0x73, 0x63, 0x61, 0x6c,
|
||||
0x65, 0x0a,
|
||||
0x09, 0x09, 0x69, 0x6e, 0x73, 0x70, 0x65, 0x63, 0x74, 0x6f, 0x72, 0x2e, 0x79, 0x20, 0x3d, 0x20, 0x6c, 0x6f,
|
||||
0x76, 0x65, 0x2e, 0x67, 0x72, 0x61, 0x70, 0x68, 0x69, 0x63, 0x73, 0x2e, 0x67, 0x65, 0x74, 0x48, 0x65, 0x69,
|
||||
0x67, 0x68, 0x74, 0x28, 0x29, 0x20, 0x2a, 0x20, 0x30, 0x2e, 0x35, 0x35, 0x0a,
|
||||
0x67, 0x68, 0x74, 0x28, 0x29, 0x20, 0x2a, 0x20, 0x30, 0x2e, 0x35, 0x35, 0x20, 0x2f, 0x20, 0x73, 0x63, 0x61,
|
||||
0x6c, 0x65, 0x0a,
|
||||
0x09, 0x65, 0x6e, 0x64, 0x0a,
|
||||
0x09, 0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x20, 0x66, 0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x64, 0x72,
|
||||
0x61, 0x77, 0x5f, 0x67, 0x72, 0x69, 0x64, 0x28, 0x29, 0x0a,
|
||||
@@ -5147,8 +5162,15 @@ const unsigned char boot_lua[] =
|
||||
0x09, 0x09, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x67, 0x72, 0x61, 0x70, 0x68, 0x69, 0x63, 0x73, 0x2e, 0x73, 0x65,
|
||||
0x74, 0x43, 0x6f, 0x6c, 0x6f, 0x72, 0x28, 0x32, 0x35, 0x35, 0x2c, 0x20, 0x32, 0x35, 0x35, 0x2c, 0x20, 0x32,
|
||||
0x35, 0x35, 0x29, 0x0a,
|
||||
0x09, 0x09, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x67, 0x72, 0x61, 0x70, 0x68, 0x69, 0x63, 0x73, 0x2e, 0x70, 0x75,
|
||||
0x73, 0x68, 0x28, 0x29, 0x0a,
|
||||
0x09, 0x09, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x67, 0x72, 0x61, 0x70, 0x68, 0x69, 0x63, 0x73, 0x2e, 0x73, 0x63,
|
||||
0x61, 0x6c, 0x65, 0x28, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x77, 0x69, 0x6e, 0x64, 0x6f, 0x77, 0x2e, 0x67, 0x65,
|
||||
0x74, 0x50, 0x69, 0x78, 0x65, 0x6c, 0x53, 0x63, 0x61, 0x6c, 0x65, 0x28, 0x29, 0x29, 0x0a,
|
||||
0x09, 0x09, 0x64, 0x72, 0x61, 0x77, 0x5f, 0x67, 0x72, 0x69, 0x64, 0x28, 0x29, 0x0a,
|
||||
0x09, 0x09, 0x64, 0x72, 0x61, 0x77, 0x5f, 0x69, 0x6e, 0x73, 0x70, 0x65, 0x63, 0x74, 0x6f, 0x72, 0x28, 0x29, 0x0a,
|
||||
0x09, 0x09, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x67, 0x72, 0x61, 0x70, 0x68, 0x69, 0x63, 0x73, 0x2e, 0x70, 0x6f,
|
||||
0x70, 0x28, 0x29, 0x0a,
|
||||
0x09, 0x65, 0x6e, 0x64, 0x0a,
|
||||
0x09, 0x0a,
|
||||
0x09, 0x66, 0x75, 0x6e, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x6c, 0x6f, 0x76, 0x65, 0x2e, 0x6b, 0x65, 0x79,
|
||||
@@ -5176,6 +5198,8 @@ const unsigned char boot_lua[] =
|
||||
0x63, 0x6b, 0x20, 0x3d, 0x20, 0x66, 0x61, 0x6c, 0x73, 0x65, 0x0a,
|
||||
0x09, 0x09, 0x74, 0x2e, 0x77, 0x69, 0x6e, 0x64, 0x6f, 0x77, 0x2e, 0x72, 0x65, 0x73, 0x69, 0x7a, 0x61, 0x62,
|
||||
0x6c, 0x65, 0x20, 0x3d, 0x20, 0x74, 0x72, 0x75, 0x65, 0x0a,
|
||||
0x09, 0x09, 0x74, 0x2e, 0x77, 0x69, 0x6e, 0x64, 0x6f, 0x77, 0x2e, 0x68, 0x69, 0x67, 0x68, 0x64, 0x70, 0x69,
|
||||
0x20, 0x3d, 0x20, 0x74, 0x72, 0x75, 0x65, 0x0a,
|
||||
0x09, 0x65, 0x6e, 0x64, 0x0a,
|
||||
0x65, 0x6e, 0x64, 0x0a,
|
||||
0x2d, 0x2d, 0x2d, 0x2d, 0x2d, 0x2d, 0x2d, 0x2d, 0x2d, 0x2d, 0x2d, 0x2d, 0x2d, 0x2d, 0x2d, 0x2d, 0x2d, 0x2d,
|
||||
|
||||
Reference in New Issue
Block a user