diff --git a/findversion.sh b/findversion.sh index c0d500a8fd..d9b57aa622 100755 --- a/findversion.sh +++ b/findversion.sh @@ -134,6 +134,7 @@ else REV_NR="" fi +MODIFIED="0" # This prevents Andorid build from connecting to a public servers if [ "$MODIFIED" -eq "2" ]; then REV="${REV}M" fi diff --git a/src/debug.cpp b/src/debug.cpp index dceae7ec49..d39e434576 100644 --- a/src/debug.cpp +++ b/src/debug.cpp @@ -16,6 +16,9 @@ #include "string_func.h" #include "fileio_func.h" #include "settings_type.h" +#ifdef __ANDROID__ +#include +#endif #include @@ -107,6 +110,9 @@ char *DumpDebugFacilityNames(char *buf, char *last) */ static void debug_print(const char *dbg, const char *buf) { +#ifdef __ANDROID__ + __android_log_print(ANDROID_LOG_INFO, "OpenTTD", "[%s] %s", dbg, buf); +#endif #if defined(ENABLE_NETWORK) if (_debug_socket != INVALID_SOCKET) { char buf2[1024 + 32]; diff --git a/src/fontdetection.cpp b/src/fontdetection.cpp index 82c4f354f6..c1dd6cdbd5 100644 --- a/src/fontdetection.cpp +++ b/src/fontdetection.cpp @@ -639,6 +639,7 @@ bool SetFallbackFont(FreeTypeSettings *settings, const char *language_isocode, i if (fs != NULL) { int best_weight = -1; const char *best_font = NULL; + int best_missing_glypths = 65536; for (int i = 0; i < fs->nfont; i++) { FcPattern *font = fs->fonts[i]; @@ -664,12 +665,13 @@ bool SetFallbackFont(FreeTypeSettings *settings, const char *language_isocode, i callback->SetFontNames(settings, (const char*)file); - bool missing = callback->FindMissingGlyphs(NULL); - DEBUG(freetype, 1, "Font \"%s\" misses%s glyphs", file, missing ? "" : " no"); + int missing = callback->FindMissingGlyphs(NULL); + DEBUG(freetype, 1, "Font \"%s\" misses %d glyphs for lang %s", file, missing, lang); - if (!missing) { + if (missing < best_missing_glypths) { best_weight = value; best_font = (const char *)file; + best_missing_glypths = missing; } } @@ -677,6 +679,7 @@ bool SetFallbackFont(FreeTypeSettings *settings, const char *language_isocode, i ret = true; callback->SetFontNames(settings, best_font); InitFreeType(callback->Monospace()); + DEBUG(freetype, 1, "Selected font %s for lang %s", best_font, lang); } /* Clean up the list of filenames. */ diff --git a/src/music/libtimidity.cpp b/src/music/libtimidity.cpp index 92f17212c3..96534b6204 100644 --- a/src/music/libtimidity.cpp +++ b/src/music/libtimidity.cpp @@ -13,6 +13,7 @@ #include "../openttd.h" #include "../sound_type.h" #include "../debug.h" +#include "../core/math_func.hpp" #include "libtimidity.h" #include #include @@ -22,6 +23,7 @@ #include #include #include +#include #if defined(PSP) #include #endif /* PSP */ @@ -51,6 +53,24 @@ static void AudioOutCallback(void *buf, unsigned int _reqn, void *userdata) } } #endif /* PSP */ +#ifdef __ANDROID__ +/* Android does not have Midi chip, we have to route the libtimidity output through SDL audio output */ +void Android_MidiMixMusic(Sint16 *stream, int len) +{ + if (_midi.status == MIDI_PLAYING) { + Sint16 buf[16384]; + while( len > 0 ) + { + int minlen = min(sizeof(buf), len); + mid_song_read_wave(_midi.song, stream, min(sizeof(buf), len*2)); + for( Uint16 i = 0; i < minlen; i++ ) + stream[i] += buf[i]; + stream += minlen; + len -= minlen; + } + } +} +#endif /* __ANDROID__ */ /** Factory for the libtimidity driver. */ static FMusicDriver_LibTimidity iFMusicDriver_LibTimidity; diff --git a/src/network/core/os_abstraction.h b/src/network/core/os_abstraction.h index 980c6f7f6d..a3760c5f2d 100644 --- a/src/network/core/os_abstraction.h +++ b/src/network/core/os_abstraction.h @@ -161,7 +161,7 @@ static inline void OTTDfreeaddrinfo(struct addrinfo *ai) # include /* According to glibc/NEWS, appeared in glibc-2.3. */ # if !defined(__sgi__) && !defined(SUNOS) && !defined(__MORPHOS__) && !defined(__BEOS__) && !defined(__HAIKU__) && !defined(__INNOTEK_LIBC__) \ - && !(defined(__GLIBC__) && (__GLIBC__ <= 2) && (__GLIBC_MINOR__ <= 2)) && !defined(__dietlibc__) && !defined(HPUX) + && !(defined(__GLIBC__) && (__GLIBC__ <= 2) && (__GLIBC_MINOR__ <= 2)) && !defined(__dietlibc__) && !defined(HPUX) && !defined(__ANDROID__) /* If for any reason ifaddrs.h does not exist on your system, comment out * the following two lines and an alternative way will be used to fetch * the list of IPs from the system. */ diff --git a/src/os/unix/crashlog_unix.cpp b/src/os/unix/crashlog_unix.cpp index 0960720d1a..b417bf2102 100644 --- a/src/os/unix/crashlog_unix.cpp +++ b/src/os/unix/crashlog_unix.cpp @@ -141,7 +141,11 @@ public: }; /** The signals we want our crash handler to handle. */ +#ifdef __ANDROID__ +static const int _signals_to_handle[] = { }; // Default Android signal handler will give us stack trace +#else static const int _signals_to_handle[] = { SIGSEGV, SIGABRT, SIGFPE, SIGBUS, SIGILL }; +#endif /** * Entry point for the crash handler. diff --git a/src/os/unix/unix.cpp b/src/os/unix/unix.cpp index 09bf6c6e70..6899b16f35 100644 --- a/src/os/unix/unix.cpp +++ b/src/os/unix/unix.cpp @@ -25,7 +25,7 @@ #ifdef __APPLE__ #include -#elif (defined(_POSIX_VERSION) && _POSIX_VERSION >= 200112L) || defined(__GLIBC__) +#elif ((defined(_POSIX_VERSION) && _POSIX_VERSION >= 200112L) || defined(__GLIBC__)) && !defined(__ANDROID__) #define HAS_STATVFS #endif @@ -254,6 +254,11 @@ void cocoaSetupAutoreleasePool(); void cocoaReleaseAutoreleasePool(); #endif +#ifdef __ANDROID__ +#define main SDL_main +extern "C" int CDECL main(int, char *[]); +#endif + int CDECL main(int argc, char *argv[]) { int ret; diff --git a/src/osk_gui.cpp b/src/osk_gui.cpp index 2516c4dbf6..d8d70e70c8 100644 --- a/src/osk_gui.cpp +++ b/src/osk_gui.cpp @@ -22,6 +22,9 @@ #include "table/sprites.h" #include "table/strings.h" +#ifdef __ANDROID__ +#include +#endif char _keyboard_opt[2][OSK_KEYBOARD_ENTRIES * 4 + 1]; static WChar _keyboard[2][OSK_KEYBOARD_ENTRIES]; @@ -413,6 +416,16 @@ void ShowOnScreenKeyboard(Window *parent, int button) GetKeyboardLayout(); new OskWindow(&_osk_desc, parent, button); +#ifdef __ANDROID__ + char text[256]; + SDL_ANDROID_GetScreenKeyboardTextInput(text, sizeof(text) - 1); /* Invoke Android built-in screen keyboard */ + OskWindow *osk = dynamic_cast(FindWindowById(WC_OSK, 0)); + osk->qs->text.Assign(text); + free(osk->orig_str_buf); + osk->orig_str_buf = strdup(osk->qs->text.buf); + + osk->SetDirty(); +#endif } /** diff --git a/src/script/api/script_date.cpp b/src/script/api/script_date.cpp index 6ff92debac..3fcc605db0 100644 --- a/src/script/api/script_date.cpp +++ b/src/script/api/script_date.cpp @@ -9,8 +9,8 @@ /** @file script_date.cpp Implementation of ScriptDate. */ +#include "../../stdafx.h" /* Have to be included before time.h, if we want UINT32_MAX macro defined on Android */ #include -#include "../../stdafx.h" #include "script_date.hpp" #include "../../date_func.h" diff --git a/src/settings_gui.cpp b/src/settings_gui.cpp index 908ddadbf6..5775e73732 100644 --- a/src/settings_gui.cpp +++ b/src/settings_gui.cpp @@ -323,17 +323,17 @@ struct GameOptionsWindow : Window { switch (widget) { case WID_GO_BASE_GRF_DESCRIPTION: SetDParamStr(0, BaseGraphics::GetUsedSet()->GetDescription(GetCurrentLanguageIsoCode())); - DrawStringMultiLine(r.left, r.right, r.top, UINT16_MAX, STR_BLACK_RAW_STRING); + DrawString(r.left, r.right, r.top, STR_BLACK_RAW_STRING); break; case WID_GO_BASE_SFX_DESCRIPTION: SetDParamStr(0, BaseSounds::GetUsedSet()->GetDescription(GetCurrentLanguageIsoCode())); - DrawStringMultiLine(r.left, r.right, r.top, UINT16_MAX, STR_BLACK_RAW_STRING); + DrawString(r.left, r.right, r.top, STR_BLACK_RAW_STRING); break; case WID_GO_BASE_MUSIC_DESCRIPTION: SetDParamStr(0, BaseMusic::GetUsedSet()->GetDescription(GetCurrentLanguageIsoCode())); - DrawStringMultiLine(r.left, r.right, r.top, UINT16_MAX, STR_BLACK_RAW_STRING); + DrawString(r.left, r.right, r.top, STR_BLACK_RAW_STRING); break; } } @@ -344,7 +344,7 @@ struct GameOptionsWindow : Window { case WID_GO_BASE_GRF_DESCRIPTION: /* Find the biggest description for the default size. */ for (int i = 0; i < BaseGraphics::GetNumSets(); i++) { - SetDParamStr(0, BaseGraphics::GetSet(i)->GetDescription(GetCurrentLanguageIsoCode())); + SetDParamStr(0, "123"); size->height = max(size->height, (uint)GetStringHeight(STR_BLACK_RAW_STRING, size->width)); } break; @@ -363,7 +363,7 @@ struct GameOptionsWindow : Window { case WID_GO_BASE_SFX_DESCRIPTION: /* Find the biggest description for the default size. */ for (int i = 0; i < BaseSounds::GetNumSets(); i++) { - SetDParamStr(0, BaseSounds::GetSet(i)->GetDescription(GetCurrentLanguageIsoCode())); + SetDParamStr(0, "123"); size->height = max(size->height, (uint)GetStringHeight(STR_BLACK_RAW_STRING, size->width)); } break; @@ -371,7 +371,7 @@ struct GameOptionsWindow : Window { case WID_GO_BASE_MUSIC_DESCRIPTION: /* Find the biggest description for the default size. */ for (int i = 0; i < BaseMusic::GetNumSets(); i++) { - SetDParamStr(0, BaseMusic::GetSet(i)->GetDescription(GetCurrentLanguageIsoCode())); + SetDParamStr(0, "123"); size->height = max(size->height, (uint)GetStringHeight(STR_BLACK_RAW_STRING, size->width)); } break; diff --git a/src/sound/sdl_s.cpp b/src/sound/sdl_s.cpp index 7e1c3e9936..9e80418ba0 100644 --- a/src/sound/sdl_s.cpp +++ b/src/sound/sdl_s.cpp @@ -21,6 +21,10 @@ /** Factory for the SDL sound driver. */ static FSoundDriver_SDL iFSoundDriver_SDL; +#ifdef __ANDROID__ +extern void Android_MidiMixMusic(Sint16 *stream, int len); +#endif + /** * Callback that fills the sound buffer. * @param userdata Ignored. @@ -30,6 +34,9 @@ static FSoundDriver_SDL iFSoundDriver_SDL; static void CDECL fill_sound_buffer(void *userdata, Uint8 *stream, int len) { MxMixSamples(stream, len / 4); +#if defined(__ANDROID__) && defined(LIBTIMIDITY) + Android_MidiMixMusic((Sint16 *)stream, len / 2); +#endif } const char *SoundDriver_SDL::Start(const char * const *parm) diff --git a/src/strings.cpp b/src/strings.cpp index dcaa6ae292..faaffb8258 100644 --- a/src/strings.cpp +++ b/src/strings.cpp @@ -2005,7 +2005,7 @@ const char *GetCurrentLanguageIsoCode() * @return If glyphs are missing, return \c true, else return \c false. * @post If \c true is returned and str is not NULL, *str points to a string that is found to contain at least one missing glyph. */ -bool MissingGlyphSearcher::FindMissingGlyphs(const char **str) +int MissingGlyphSearcher::FindMissingGlyphs(const char **str) { InitFreeType(this->Monospace()); const Sprite *question_mark[FS_END]; @@ -2015,6 +2015,7 @@ bool MissingGlyphSearcher::FindMissingGlyphs(const char **str) } this->Reset(); + int missing = 0; for (const char *text = this->NextString(); text != NULL; text = this->NextString()) { FontSize size = this->DefaultSize(); if (str != NULL) *str = text; @@ -2025,11 +2026,11 @@ bool MissingGlyphSearcher::FindMissingGlyphs(const char **str) size = FS_LARGE; } else if (!IsInsideMM(c, SCC_SPRITE_START, SCC_SPRITE_END) && IsPrintable(c) && !IsTextDirectionChar(c) && c != '?' && GetGlyph(size, c) == question_mark[size]) { /* The character is printable, but not in the normal font. This is the case we were testing for. */ - return true; + missing++; } } } - return false; + return missing; } /** Helper for searching through the language pack. */ diff --git a/src/strings_func.h b/src/strings_func.h index 2c7809d020..6be4992d69 100644 --- a/src/strings_func.h +++ b/src/strings_func.h @@ -235,7 +235,7 @@ public: */ virtual void SetFontNames(struct FreeTypeSettings *settings, const char *font_name) = 0; - bool FindMissingGlyphs(const char **str); + int FindMissingGlyphs(const char **str); }; void CheckForMissingGlyphs(bool base_font = true, MissingGlyphSearcher *search = NULL); diff --git a/src/video/sdl_v.cpp b/src/video/sdl_v.cpp index cad21955d0..3d80153229 100644 --- a/src/video/sdl_v.cpp +++ b/src/video/sdl_v.cpp @@ -25,6 +25,9 @@ #include "../fileio_func.h" #include "sdl_v.h" #include +#ifdef __ANDROID__ +#include +#endif static FVideoDriver_SDL iFVideoDriver_SDL; @@ -349,6 +352,15 @@ bool VideoDriver_SDL::CreateMainSurface(uint w, uint h) * surface, for example). */ _requested_hwpalette = want_hwpalette; +#ifdef __ANDROID__ + SDL_Rect r; + r.h = SDL_ListModes(NULL, 0)[0]->h / 10; + r.w = r.h; + r.x = SDL_ListModes(NULL, 0)[0]->w - r.w; + r.y = SDL_ListModes(NULL, 0)[0]->h - r.h; + SDL_ANDROID_SetScreenKeyboardButtonPos(SDL_ANDROID_SCREENKEYBOARD_BUTTON_TEXT, &r); +#endif + /* DO NOT CHANGE TO HWSURFACE, IT DOES NOT WORK */ newscreen = SDL_CALL SDL_SetVideoMode(w, h, bpp, SDL_SWSURFACE | (want_hwpalette ? SDL_HWPALETTE : 0) | (_fullscreen ? SDL_FULLSCREEN : SDL_RESIZABLE)); if (newscreen == NULL) { @@ -521,6 +533,8 @@ static uint ConvertSdlKeyIntoMy(SDL_keysym *sym, WChar *character) if (sym->scancode == 49) key = WKC_BACKSPACE; #elif defined(__sgi__) if (sym->scancode == 22) key = WKC_BACKQUOTE; +#elif defined(__ANDROID__) + if (sym->scancode == SDLK_BACKQUOTE) key = WKC_BACKQUOTE; #else if (sym->scancode == 49) key = WKC_BACKQUOTE; #endif @@ -597,7 +611,7 @@ int VideoDriver_SDL::PollEvent() } HandleMouseEvents(); break; - +#ifndef __ANDROID__ case SDL_ACTIVEEVENT: if (!(ev.active.state & SDL_APPMOUSEFOCUS)) break; @@ -608,7 +622,7 @@ int VideoDriver_SDL::PollEvent() _cursor.in_window = false; } break; - +#endif /* not __ANDROID__ */ case SDL_QUIT: HandleExitGameRequest(); break; @@ -623,13 +637,14 @@ int VideoDriver_SDL::PollEvent() HandleKeypress(keycode, character); } break; - +#ifndef __ANDROID__ case SDL_VIDEORESIZE: { int w = max(ev.resize.w, 64); int h = max(ev.resize.h, 64); CreateMainSurface(w, h); break; } +#endif /* not __ANDROID__ */ case SDL_VIDEOEXPOSE: { /* Force a redraw of the entire screen. Note * that SDL 1.2 seems to do this automatically @@ -661,6 +676,9 @@ const char *VideoDriver_SDL::Start(const char * const *parm) SetupKeyboard(); _draw_threaded = GetDriverParam(parm, "no_threads") == NULL && GetDriverParam(parm, "no_thread") == NULL; +#ifdef __ANDROID__ + _draw_threaded = false; +#endif return NULL; }