50#include <wx/apptrait.h>
51#include <wx/stdpaths.h>
52#include <wx/filename.h>
53#include <wx/tokenzr.h>
54#include <wx/textfile.h>
55#include <wx/jsonval.h>
56#include <wx/jsonreader.h>
84#include "snd_config.h"
85#include "std_filesystem.h"
90#include "androidUTIL.h"
98#ifdef OCPN_USE_CRASHREPORT
120void appendOSDirSlash(wxString *pString);
123struct sigaction sa_all;
124struct sigaction sa_all_old;
131#if wxUSE_XLOCALE || !wxCHECK_VERSION(3, 0, 0)
132extern wxLocale *plocale_def_lang;
143static const char *
const DEFAULT_XDG_DATA_DIRS =
144 "~/.local/share:/usr/local/share:/usr/share";
147static const char PATH_SEP =
';';
149static const char PATH_SEP =
':';
153constexpr int kStatFieldCount = 2;
155constexpr int kStatFieldCount = 5;
158static bool checkIfFlatpacked() {
160 if (!wxGetEnv(
"FLATPAK_ID", &
id)) {
163 return id ==
"org.opencpn.OpenCPN";
166OCPNPlatform::OCPNPlatform() {
168 m_bdisableWindowsDisplayEnum =
false;
169 m_monitorWidth = m_monitorHeight = 0;
172 m_displaySizeMMOverride.push_back(0);
174 m_pluginDataPath =
"";
177OCPNPlatform::~OCPNPlatform() {
189int MyNewHandler(
size_t size) {
191 throw std::bad_alloc();
212void catch_signals(
int signo) {
225 top_frame::Get()->FastClose();
232 top_frame::Get()->FastClose();
243#ifdef OCPN_USE_CRASHREPORT
245int CALLBACK CrashCallback(CR_CRASH_CALLBACK_INFO *pInfo) {
246 wxLog::GetActiveTarget()->Flush();
247 return CR_CB_DODEFAULT;
252void OCPNPlatform::Initialize_1() {
253#ifdef OCPN_USE_CRASHREPORT
257 CR_INSTALL_INFO info;
258 memset(&info, 0,
sizeof(CR_INSTALL_INFO));
259 info.cb =
sizeof(CR_INSTALL_INFO);
260 info.pszAppName = L
"OpenCPN";
262 info.pszAppVersion = wxString(VERSION_FULL).c_str();
264 int type = MiniDumpNormal;
267 type |= MiniDumpWithDataSegs;
278 info.uMiniDumpType = (MINIDUMP_TYPE)type;
281 info.dwFlags = CR_INST_ALL_POSSIBLE_HANDLERS;
284 info.dwFlags &= ~CR_INST_NEW_OPERATOR_ERROR_HANDLER;
287 info.dwFlags |= CR_INST_ALLOW_ATTACH_MORE_FILES;
290 info.dwFlags |= CR_INST_SHOW_ADDITIONAL_INFO_FIELDS;
294 if (g_bEmailCrashReport) {
295 info.pszUrl = L
"https://bigdumboat.com/crashrpt/ocpn_crashrpt.php";
296 info.uPriorities[CR_HTTP] = 3;
298 info.dwFlags |= CR_INST_DONT_SEND_REPORT;
299 info.uPriorities[CR_HTTP] = CR_NEGATIVE_PRIORITY;
302 info.uPriorities[CR_SMTP] =
303 CR_NEGATIVE_PRIORITY;
304 info.uPriorities[CR_SMAPI] =
305 CR_NEGATIVE_PRIORITY;
307 wxStandardPaths &crash_std_path =
g_Platform->GetStdPaths();
309 wxString crash_rpt_save_locn = crash_std_path.GetConfigDir();
311 wxFileName exec_path_crash(crash_std_path.GetExecutablePath());
312 crash_rpt_save_locn =
313 exec_path_crash.GetPath(wxPATH_GET_VOLUME | wxPATH_GET_SEPARATOR);
316 wxString locn = crash_rpt_save_locn +
"\\CrashReports";
318 if (!wxDirExists(locn)) wxMkdir(locn);
320 if (wxDirExists(locn)) {
321 wxCharBuffer buf = locn.ToUTF8();
323 if (buf && (locn.Length() <
sizeof(wlocn))) {
324 MultiByteToWideChar(0, 0, buf.data(), -1, wlocn,
sizeof(wlocn) - 1);
325 info.pszErrorReportSaveDir = (LPCWSTR)wlocn;
330 wxFileName exec_path_crash(crash_std_path.GetExecutablePath());
331 wxString policy_file =
332 exec_path_crash.GetPath(wxPATH_GET_VOLUME | wxPATH_GET_SEPARATOR);
333 policy_file +=
"PrivacyPolicy.txt";
334 policy_file.Prepend(
"file:");
336 info.pszPrivacyPolicyURL = policy_file.c_str();
339 int nResult = crInstall(&info);
342 crGetLastErrorMsg(buff, 256);
349 crSetCrashCallback(CrashCallback, NULL);
352 crAddScreenshot2(CR_AS_PROCESS_WINDOWS | CR_AS_USE_JPEG_FORMAT, 95);
355 wxString home_data_crash = crash_std_path.GetConfigDir();
357 wxFileName f(crash_std_path.GetExecutablePath());
358 home_data_crash = f.GetPath();
360 appendOSDirSlash(&home_data_crash);
362 wxString config_crash =
"opencpn.ini";
363 config_crash.Prepend(home_data_crash);
364 crAddFile2(config_crash.c_str(), NULL, NULL,
365 CR_AF_MISSING_FILE_OK | CR_AF_ALLOW_DELETE);
367 wxString log_crash =
"opencpn.log";
368 log_crash.Prepend(home_data_crash);
369 crAddFile2(log_crash.c_str(), NULL, NULL,
370 CR_AF_MISSING_FILE_OK | CR_AF_ALLOW_DELETE);
376#if wxUSE_ON_FATAL_EXCEPTION
378 wxHandleFatalExceptions(
true);
384 _set_new_handler(MyNewHandler);
394 HANDLE hProc = GetCurrentProcess();
398 DuplicateHandle( hProc, hProc, hProc, &hDup, 0, FALSE, DUPLICATE_SAME_ACCESS );
401 GetProcessAffinityMask( hDup, &procMask, &sysMask );
405 if( ( procMask & 1 ) == 1 ) newMask = 1;
407 if( ( procMask & 2 ) == 2 ) newMask = 2;
409 if( ( procMask & 4 ) == 4 ) newMask = 4;
411 if( ( procMask & 8 ) == 8 ) newMask = 8;
414 BOOL res = SetProcessAffinityMask( hDup, (DWORD_PTR) newMask );
428 wxPlatformInfo Platform;
429 if (Platform.GetOperatingSystemId() == wxOS_WINDOWS_9X)
430 SetUnhandledExceptionFilter(&MyUnhandledExceptionFilter);
441 sa_all.sa_handler = catch_signals;
442 sigemptyset(&sa_all.sa_mask);
448 sigaction(SIGUSR1, NULL,
452 sigaction(SIGUSR1, &sa_all, NULL);
453 sigaction(SIGUSR1, NULL,
456 sigaction(SIGTERM, &sa_all, NULL);
457 sigaction(SIGTERM, NULL, &sa_all_old);
459 sigaction(SIGHUP, &sa_all, NULL);
460 sigaction(SIGHUP, NULL, &sa_all_old);
465 qDebug() <<
"Initialize_1()";
475void OCPNPlatform::Initialize_2() {
477 wxLogMessage(androidGetDeviceInfo());
481 wxChar sep = wxFileName::GetPathSeparator();
484 if (ChartDir.Last() != sep) ChartDir.Append(sep);
485 ChartDir.Append(
"Charts");
486 if (!::wxDirExists(ChartDir)) {
491 if (GRIBDir.Last() != sep) GRIBDir.Append(sep);
492 GRIBDir.Append(
"GRIBS");
493 if (!::wxDirExists(GRIBDir)) {
498 if (VDRDir.Last() != sep) VDRDir.Append(sep);
499 VDRDir.Append(
"VDR");
500 if (!::wxDirExists(VDRDir)) {
505 if (g_Android_SDK_Version >= 30) {
506 if (!g_gpx_path.StartsWith(androidGetDocumentsDirectory())) {
507 g_gpx_path = androidGetDocumentsDirectory();
514 g_toolbar_scalefactor = GetToolbarScaleFactor(g_GUIScaleFactor);
516 if (!configdir.DirExists()) {
517 if (!configdir.Mkdir()) {
518 auto msg = std::string(
"Cannot create config directory: ");
519 wxLogWarning(msg + configdir.GetFullPath());
526void OCPNPlatform::Initialize_3() {
527 bool bcapable = IsGLCapable();
533 bool bAndroid =
false;
542 g_bdisable_opengl =
false;
550 if ((g_bFirstRun || g_bUpgradeInProcess || bAndroid) && bcapable) {
554 g_GLOptions.m_bUseAcceleratedPanning =
true;
555 g_GLOptions.m_bTextureCompression =
true;
556 g_GLOptions.m_bTextureCompressionCaching =
true;
558 g_GLOptions.m_iTextureDimension = 512;
559 g_GLOptions.m_iTextureMemorySize = 64;
561 g_GLOptions.m_GLPolygonSmoothing =
true;
562 g_GLOptions.m_GLLineSmoothing =
true;
572 if (g_bFirstRun || g_bUpgradeInProcess) {
577 g_FlushNavobjChangesTimeout = 300;
581void OCPNPlatform::Initialize_4() {
583 if (
pSelect)
pSelect->SetSelectPixelRadius(wxMax(25, 6.0 * getAndroidDPmm()));
585 pSelectTC->SetSelectPixelRadius(wxMax(25, 6.0 * getAndroidDPmm()));
587 pSelectAIS->SetSelectPixelRadius(wxMax(25, 6.0 * getAndroidDPmm()));
594 options_lastPage = 1;
598void OCPNPlatform::OnExit_1() {}
600void OCPNPlatform::OnExit_2() {
601#ifdef OCPN_USE_CRASHREPORT
611bool HasGLExt(
wxJSONValue &glinfo,
const std::string ext) {
612 if (!glinfo.
HasMember(
"GL_EXTENSIONS")) {
615 for (
int i = 0; i < glinfo[
"GL_EXTENSIONS"].
Size(); i++) {
616 if (glinfo[
"GL_EXTENSIONS"][i].AsString() == ext) {
623bool OCPNPlatform::BuildGLCaps(
void *pbuf) {
625 fs::path ep(GetExePath().ToStdString());
627 std::string gl_util_exe =
"opencpn-glutil";
629 std::string gl_util_exe =
"opencpn-glutil.exe";
631 fs::path gl_util_path = ep.parent_path().append(gl_util_exe);
633 if (!fs::exists(gl_util_path)) {
635 ep.parent_path().parent_path().append(
"libexec").append(gl_util_exe);
637 if (!fs::exists(gl_util_path)) {
640 wxLogMessage(
"OpenGL test utility not found at %s.", gl_util_path.c_str());
645 .append(
"gl_caps.json")
648 wxString cmd = wxString::Format(
"\"%s\" opengl-info \"%s\"",
649 gl_util_path.c_str(), gl_json.c_str());
651 wxLogMessage(
"Starting OpenGL test utility: %s", cmd);
653 wxArrayString output;
654 if (
long res = wxExecute(cmd, output); res != 0) {
655 wxLogMessage(
"OpenGL test utility failed with exit code %d", res);
656 for (
const auto &l : output) {
662 wxFileInputStream fis(gl_json);
665 reader.
Parse(fis, &root);
667 wxLogMessage(
"Failed to parse JSON output from OpenGL test utility.");
668 for (
const auto &l : reader.GetErrors()) {
677 pcaps->Renderer = root[
"GL_RENDERER"].
AsString();
679 wxLogMessage(
"GL_RENDERER not found.");
683 pcaps->Version = root[
"GL_VERSION"].
AsString();
685 wxLogMessage(
"GL_VERSION not found.");
688 if (root.
HasMember(
"GL_SHADING_LANGUAGE_VERSION")) {
689 pcaps->GLSL_Version = root[
"GL_SHADING_LANGUAGE_VERSION"].
AsString();
691 wxLogMessage(
"GL_SHADING_LANGUAGE_VERSION not found.");
695 if (!root[
"GL_USABLE"].AsBool()) {
696 wxLogMessage(
"OpenGL test utility reports that OpenGL is not usable.");
700 wxLogMessage(
"GL_USABLE not found.");
703 pcaps->dGLSL_Version = 0;
704 pcaps->dGLSL_Version = ::atof(pcaps->GLSL_Version.c_str());
705 if (pcaps->dGLSL_Version < 1.2) {
707 msg.Printf(
"GLCaps Probe: OpenGL-> GLSL Version reported: ");
708 msg += wxString(pcaps->GLSL_Version.c_str());
709 msg +=
"\n OpenGL disabled due to insufficient OpenGL capabilities";
711 pcaps->bCanDoGLSL =
false;
714 pcaps->bCanDoGLSL =
true;
715 if (HasGLExt(root,
"GL_ARB_texture_non_power_of_two")) {
716 pcaps->TextureRectangleFormat = GL_TEXTURE_2D;
717 }
else if (HasGLExt(root,
"GL_OES_texture_npot")) {
718 pcaps->TextureRectangleFormat = GL_TEXTURE_2D;
719 }
else if (HasGLExt(root,
"GL_ARB_texture_rectangle")) {
720 pcaps->TextureRectangleFormat = GL_TEXTURE_RECTANGLE_ARB;
723 pcaps->bOldIntel =
false;
725 pcaps->bCanDoFBO = HasGLExt(root,
"GL_EXT_framebuffer_object");
726 if (!pcaps->TextureRectangleFormat) {
727 pcaps->bCanDoFBO =
false;
730 pcaps->bCanDoVBO = HasGLExt(
731 root,
"GL_ARB_vertex_buffer_object");
734 top_frame::Get()->Show();
739 top_frame::Get()->Show();
743 wxGLContext *pctx =
new wxGLContext(tcanvas);
744 tcanvas->SetCurrent(*pctx);
748 char *str = (
char *)glGetString(GL_RENDERER);
750 wxLogMessage(
"GL_RENDERER not found.");
755 pcaps->Renderer = std::string(str);
757 char *stv = (
char *)glGetString(GL_VERSION);
759 wxLogMessage(
"GL_VERSION not found");
764 pcaps->Version = std::string(stv);
766 char *stsv = (
char *)glGetString(GL_SHADING_LANGUAGE_VERSION);
768 wxLogMessage(
"GL_SHADING_LANGUAGE_VERSION not found");
773 pcaps->GLSL_Version = std::string(stsv);
775 pcaps->dGLSL_Version = 0;
776 pcaps->dGLSL_Version = ::atof(pcaps->GLSL_Version.c_str());
778 if (pcaps->dGLSL_Version < 1.2) {
780 msg.Printf(
"GLCaps Probe: OpenGL-> GLSL Version reported: ");
781 msg += wxString(pcaps->GLSL_Version.c_str());
782 msg +=
"\n OpenGL disabled due to insufficient OpenGL capabilities";
784 pcaps->bCanDoGLSL =
false;
790 pcaps->bCanDoGLSL =
true;
792 if (QueryExtension(
"GL_ARB_texture_non_power_of_two"))
793 pcaps->TextureRectangleFormat = GL_TEXTURE_2D;
794 else if (QueryExtension(
"GL_OES_texture_npot"))
795 pcaps->TextureRectangleFormat = GL_TEXTURE_2D;
796 else if (QueryExtension(
"GL_ARB_texture_rectangle"))
797 pcaps->TextureRectangleFormat = GL_TEXTURE_RECTANGLE_ARB;
799 pcaps->bOldIntel =
false;
802 pcaps->bCanDoVBO =
true;
804#if defined(__WXMSW__) || defined(__WXOSX__)
805 if (pcaps->bOldIntel) pcaps->bCanDoVBO =
false;
809 pcaps->bCanDoVBO =
false;
813 pcaps->bCanDoFBO =
true;
817 if (!pcaps->TextureRectangleFormat) pcaps->bCanDoFBO =
false;
820 if (!QueryExtension(
"GL_EXT_framebuffer_object")) pcaps->bCanDoFBO =
false;
830bool OCPNPlatform::IsGLCapable() {
839 if (g_bdisable_opengl)
return false;
841 wxLogMessage(
"Starting OpenGL test...");
842 wxLog::FlushActive();
846 bool bcaps = BuildGLCaps(GL_Caps);
848 wxLogMessage(
"OpenGL test complete.");
850 wxLogMessage(
"BuildGLCaps fails.");
851 wxLog::FlushActive();
859 if (!GL_Caps->bCanDoGLSL) {
865 if (!GL_Caps->bCanDoFBO) {
870 wxLogMessage(
"OpenGL determined CAPABLE.");
871 wxLog::FlushActive();
873 g_bdisable_opengl =
false;
886void OCPNPlatform::SetLocaleSearchPrefixes() {
889#if defined(__WINDOWS__)
892 wxString locale_location = GetSharedDataDir();
893 locale_location +=
"share\\locale";
894 wxLocale::AddCatalogLookupPathPrefix(locale_location);
895 wxString imsg =
"Adding catalog lookup path: ";
896 imsg += locale_location;
901 usrShare.RemoveLastDir();
902 locale_location = usrShare.GetFullPath() + (
"share\\locale");
903 wxLocale::AddCatalogLookupPathPrefix(locale_location);
904 imsg =
"Adding catalog lookup path: ";
905 imsg += locale_location;
908#elif defined(__ANDROID__)
910 wxString locale_location = GetSharedDataDir() +
"locale";
911 wxLocale::AddCatalogLookupPathPrefix(locale_location);
913#elif defined(__UNIX__) && !defined(__WINE__)
918 wxString locale_location;
919 if (!wxGetEnv(
"OPENCPN_PREFIX", &locale_location)) {
920 locale_location =
"/usr/local";
928 location.AssignDir(locale_location);
929 location.AppendDir(
"share");
930 location.SetName(
"locale");
931 locale_location = location.GetFullPath();
932 wxLocale::AddCatalogLookupPathPrefix(locale_location);
936 wxString managed_locale_location(dir +
"/locale");
937 wxLocale::AddCatalogLookupPathPrefix(managed_locale_location);
943 "/Library/Application Support/OpenCPN/Contents/Resources";
944 wxString Mac_managed_locale_location(macDir);
945 wxLocale::AddCatalogLookupPathPrefix(Mac_managed_locale_location);
951wxString OCPNPlatform::GetDefaultSystemLocale() {
952 wxLogMessage(
"Getting DefaultSystemLocale...");
954 wxString retval =
"en_US";
958 const wxLanguageInfo *languageInfo =
959 wxLocale::GetLanguageInfo(wxLANGUAGE_DEFAULT);
960 if (languageInfo) retval = languageInfo->CanonicalName;
962#if defined(__WXMSW__)
963 LANGID lang_id = GetUserDefaultUILanguage();
966 const wxLanguageInfo *languageInfoW = 0;
967 if (0 != GetLocaleInfo(MAKELCID(lang_id, SORT_DEFAULT), LOCALE_SENGLANGUAGE,
969 wxString lstring = wxString(lngcp);
971 languageInfoW = wxLocale::FindLanguageInfo(lngcp);
973 wxLogMessage(
"Found LanguageInfo for: " + lstring);
975 wxLogMessage(
"Could not find LanguageInfo for: " + lstring);
977 wxLogMessage(
"Could not get LocaleInfo, using wxLANGUAGE_DEFAULT");
978 languageInfoW = wxLocale::GetLanguageInfo(wxLANGUAGE_DEFAULT);
981 if (languageInfoW) retval = languageInfoW->CanonicalName;
984#if defined(__ANDROID__)
985 retval = androidGetAndroidSystemLocale();
993#if wxUSE_XLOCALE || !wxCHECK_VERSION(3, 0, 0)
994wxString OCPNPlatform::GetAdjustedAppLocale() {
995 wxString adjLocale = g_locale;
1000#if defined(__WXMSW__)
1001 if (g_bFirstRun || wxIsEmpty(adjLocale)) {
1002 wxRegKey RegKey(wxString(
"HKEY_LOCAL_MACHINE\\SOFTWARE\\OpenCPN"));
1003 if (RegKey.Exists()) {
1005 "Retrieving initial language selection from Windows Registry");
1006 RegKey.QueryValue(wxString(
"InstallerLanguage"), adjLocale);
1009 if (wxIsEmpty(adjLocale)) {
1010 if (g_localeOverride.Length())
1011 adjLocale = g_localeOverride;
1013 adjLocale = GetDefaultSystemLocale();
1016#if defined(__ANDROID__)
1017 if (g_localeOverride.Length())
1018 adjLocale = g_localeOverride;
1020 adjLocale = GetDefaultSystemLocale();
1026wxString OCPNPlatform::ChangeLocale(wxString &newLocaleID,
1027 wxLocale *presentLocale,
1028 wxLocale **newLocale) {
1029 wxString return_val;
1031 wxString imsg =
"ChangeLocale: Language load for: ";
1032 imsg += newLocaleID;
1036 delete (wxLocale *)presentLocale;
1038 wxLocale *locale =
new wxLocale;
1039 if (isFlatpacked()) {
1040 std::string path(getenv(
"HOME"));
1041 path +=
"/.var/app/org.opencpn.OpenCPN/data/locale";
1042 locale->AddCatalogLookupPathPrefix(path);
1043 wxLogMessage(
"Using flatpak locales at %s", path.c_str());
1045 wxString loc_lang_canonical;
1047 const wxLanguageInfo *pli = wxLocale::FindLanguageInfo(newLocaleID);
1048 bool b_initok =
false;
1051 locale->Init(pli->Language, 1);
1055 if (!locale->IsOk()) {
1056 wxString imsg =
"ChangeLocale: could not initialize: ";
1057 imsg += newLocaleID;
1061 locale =
new wxLocale;
1062 locale->Init(pli->Language, 0);
1064 loc_lang_canonical = pli->CanonicalName;
1066 b_initok = locale->IsOk();
1073 wxString imsg =
"ChangeLocale: Fall back to en_US";
1077 locale =
new wxLocale;
1078 locale->Init(wxLANGUAGE_ENGLISH_US, 0);
1079 loc_lang_canonical =
1080 wxLocale::GetLanguageInfo(wxLANGUAGE_ENGLISH_US)->CanonicalName;
1084 wxString imsg =
"ChangeLocale: Locale Init OK for: ";
1085 imsg += loc_lang_canonical;
1099 wxString emsg =
"ERROR Loading translation catalog for: ";
1103 wxString imsg =
"Loaded translation catalog for: ";
1110 wxLogMessage(
"Loading catalog for opencpn core.");
1111 locale->AddCatalog(
"opencpn");
1113 return_val = locale->GetCanonicalName();
1116 if (return_val != GetDefaultSystemLocale())
1117 g_localeOverride = return_val;
1119 g_localeOverride =
"";
1122 *newLocale = locale;
1125 setlocale(LC_NUMERIC,
"C");
1136void OCPNPlatform::SetDefaultOptions() {
1138 g_bShowOutlines =
true;
1144 g_MarkLost_Mins = 8;
1145 g_bRemoveLost =
true;
1146 g_RemoveLost_Mins = 10;
1149 g_bSyncCogPredictors =
false;
1150 g_bHideMoored =
false;
1151 g_ShowMoored_Kts = 0.2;
1152 g_SOGminCOG_kts = 0.2;
1153 g_bTrackDaily =
false;
1155 g_bFullScreenQuilt =
true;
1156 g_bQuiltEnable =
true;
1157 g_bskew_comp =
false;
1158 g_bShowAreaNotices =
false;
1159 g_bDrawAISSize =
false;
1160 g_bDrawAISRealtime =
false;
1161 g_AIS_RealtPred_Kts = 0.7;
1162 g_bShowAISName =
false;
1163 g_nTrackPrecision = 2;
1164 g_bPreserveScaleOnX =
true;
1168 g_n_ownship_min_mm = 8;
1169 g_bShowMuiZoomButtons =
true;
1170 g_bresponsive =
false;
1174 pConfig->SetPath(
"/Settings/GlobalState");
1175 pConfig->Write(
"bShowS57Text",
true);
1176 pConfig->Write(
"bShowS57ImportantTextOnly",
false);
1177 pConfig->Write(
"nDisplayCategory", (
int)(_DisCat)OTHER);
1178 pConfig->Write(
"nSymbolStyle", (
int)(_LUPname)PAPER_CHART);
1179 pConfig->Write(
"nBoundaryStyle", (
int)(_LUPname)PLAIN_BOUNDARIES);
1181 pConfig->Write(
"bShowSoundg",
true);
1182 pConfig->Write(
"bShowMeta",
false);
1183 pConfig->Write(
"bUseSCAMIN",
true);
1184 pConfig->Write(
"bShowAtonText",
false);
1185 pConfig->Write(
"bShowLightDescription",
false);
1186 pConfig->Write(
"bExtendLightSectors",
true);
1187 pConfig->Write(
"bDeClutterText",
true);
1188 pConfig->Write(
"bShowNationalText",
true);
1190 pConfig->Write(
"S52_MAR_SAFETY_CONTOUR", 3);
1191 pConfig->Write(
"S52_MAR_SHALLOW_CONTOUR", 2);
1192 pConfig->Write(
"S52_MAR_DEEP_CONTOUR", 6);
1193 pConfig->Write(
"S52_MAR_TWO_SHADES", 0);
1194 pConfig->Write(
"S52_DEPTH_UNIT_SHOW", 1);
1196 pConfig->Write(
"ZoomDetailFactorVector", 3);
1198 pConfig->Write(
"nColorScheme", 1);
1202 g_bEnableZoomToCursor =
true;
1204 g_bShowMenuBar =
true;
1209 g_bShowMenuBar =
false;
1212 pConfig->SetPath(
"/PlugIns/chartdldr_pi.dll");
1213 pConfig->Write(
"bEnabled",
true);
1215 pConfig->SetPath(
"/PlugIns/wmm_pi.dll");
1216 pConfig->Write(
"bEnabled",
true);
1218 pConfig->SetPath(
"/Settings/WMM");
1219 pConfig->Write(
"ShowIcon",
true);
1220 pConfig->Write(
"ShowLiveIcon",
true);
1227 pConfig->SetPath(
"/PlugIns/libchartdldr_pi.dylib");
1228 pConfig->Write(
"bEnabled",
true);
1230 pConfig->SetPath(
"/PlugIns/libwmm_pi.dylib");
1231 pConfig->Write(
"bEnabled",
true);
1233 pConfig->SetPath(
"/Settings/WMM");
1234 pConfig->Write(
"ShowIcon",
true);
1235 pConfig->Write(
"ShowLiveIcon",
true);
1242 pConfig->SetPath(
"/PlugIns/libchartdldr_pi.so");
1243 pConfig->Write(
"bEnabled",
true);
1245 pConfig->SetPath(
"/PlugIns/libwmm_pi.so");
1246 pConfig->Write(
"bEnabled",
true);
1248 pConfig->SetPath(
"/Settings/WMM");
1249 pConfig->Write(
"ShowIcon",
true);
1250 pConfig->Write(
"ShowLiveIcon",
true);
1258 g_GLOptions.m_bTextureCompression = 1;
1259 g_GLOptions.m_bTextureCompressionCaching = 1;
1262 qDebug() <<
"SetDefaultOptions";
1265 g_bresponsive =
true;
1266 g_default_font_size = 18;
1269 g_bShowStatusBar =
true;
1270 g_cm93_zoom_factor = 0;
1271 g_oz_vector_scale =
false;
1272 g_fog_overzoom =
false;
1275 g_bShowMuiZoomButtons =
true;
1277 g_GUIScaleFactor = 0;
1278 g_ChartNotRenderScaleFactor = 2.0;
1282 g_toolbarConfig =
"X.....XX.......XX.XXXXXXXXXXX";
1283 g_bPermanentMOBIcon =
false;
1285 wxString sGPS =
"2;3;;0;0;;0;1;0;0;;0;;1;0;0;0;0";
1288 new_params->bEnabled =
true;
1289 TheConnectionParams().push_back(new_params);
1296 pConfig->SetPath(
"/PlugIns/libchartdldr_pi.so");
1297 pConfig->Write(
"bEnabled",
true);
1299 pConfig->SetPath(
"/PlugIns/libwmm_pi.so");
1300 pConfig->Write(
"bEnabled",
true);
1302 pConfig->SetPath(
"/Settings/WMM");
1303 pConfig->Write(
"ShowIcon",
true);
1304 pConfig->Write(
"ShowLiveIcon",
true);
1306 pConfig->SetPath(
"/PlugIns/libgrib_pi.so");
1307 pConfig->Write(
"bEnabled",
true);
1309 pConfig->SetPath(
"/PlugIns/libdashboard_pi.so");
1310 pConfig->Write(
"bEnabled",
true);
1312 pConfig->SetPath(
"/PlugIns/GRIB");
1313 pConfig->Write(
"GRIBCtrlBarPosX", 100);
1314 pConfig->Write(
"GRIBCtrlBarPosY", 0);
1316 pConfig->SetPath(
"/Settings/GRIB");
1317 pConfig->Write(
"CursorDataShown", 0);
1321 pConfig->SetPath(
"/PlugIns/liboesenc_pi.so");
1322 pConfig->Write(
"bEnabled",
true);
1324 pConfig->SetPath(
"/Settings/QTFonts");
1327 wxString str =
"en_US-b25a3899";
1328 wxString pval =
"StatusBar:Roboto,26,-1,5,75,0,0,0,0,0:rgb(0, 0, 0)";
1333 str =
"en_US-9c3b3a0d";
1334 pval =
"DialogStatusBar:Roboto,18,-1,5,50,0,0,0,0,0:rgb(0, 0, 0)";
1339 pConfig->SetPath(
"/Settings/Others");
1340 pConfig->Write(
"TrackLineColour",
"#C545C3");
1341 g_colourTrackLineColour.Set(197, 69, 195);
1343 qDebug() <<
"SetDefaultOptions.Config";
1354void OCPNPlatform::SetUpgradeOptions(wxString vNew, wxString vOld) {
1357 qDebug() <<
"Upgrade check"
1358 <<
"from: " << vOld.mb_str() <<
" to: " << vNew.mb_str();
1360 if (androidGetVersionCode() > g_AndroidVersionCode) {
1361 qDebug() <<
"Upgrade detected"
1362 <<
"from VC: " << g_AndroidVersionCode
1363 <<
" to VC: " << androidGetVersionCode();
1367 pConfig->SetPath(
"/Settings/GlobalState");
1368 pConfig->Write(
"bShowS57Text",
true);
1371 g_ChartNotRenderScaleFactor = 2.0;
1372 g_n_ownship_min_mm = 8;
1373 g_toolbarConfig =
"X.....XX.......XX.XXXXXXXXXXX";
1376 pConfig->DeleteGroup(
"/Settings/QTFonts");
1377 g_default_font_size = 20;
1380 FontMgr::Get().Shutdown();
1383 g_bShowMuiZoomButtons =
true;
1387 pInit_Chart_Dir->Clear();
1391 pConfig->SetPath(
"/Settings/WMM");
1392 pConfig->Write(
"ShowIcon",
true);
1393 pConfig->Write(
"ShowLiveIcon",
true);
1395 pConfig->SetPath(
"/Canvas/CanvasConfig1");
1396 pConfig->Write(
"canvasENCShowVisibleSectorLights", 0);
1406 AndroidRemoveSystemFile(
1407 "/data/user/0/org.opencpn.opencpn/manPlug/libchartscale_pi.so");
1411 g_colourTrackLineColour.Set(197, 69, 195);
1415 if (!vOld.IsSameAs(vNew)) {
1421 wxChar sep = wxFileName::GetPathSeparator();
1422 if (UserIconPath.Last() != sep) UserIconPath.Append(sep);
1423 UserIconPath.Append(
"UserIcons");
1425 if (!::wxDirExists(UserIconPath)) {
1426 ::wxMkdir(UserIconPath);
1431 if (LayersPath.Last() != sep) LayersPath.Append(sep);
1432 LayersPath.Append(
"layers");
1434 if (!::wxDirExists(LayersPath)) {
1435 ::wxMkdir(LayersPath);
1441 g_CmdSoundString = wxString(OCPN_SOUND_CMD);
1442 pConfig->SetPath(
"/Settings");
1443 pConfig->Write(
"CmdSoundString", g_CmdSoundString);
1447 g_bAIS_GCPA_Alert_Audio =
true;
1448 g_bAIS_SART_Alert_Audio =
true;
1449 g_bAIS_DSC_Alert_Audio =
true;
1452 g_maintoolbar_x = -1;
1456 std::vector<std::string> TCDS_temp;
1457 for (
unsigned int i = 0; i < TideCurrentDataSet.size(); i++)
1458 TCDS_temp.push_back(TideCurrentDataSet[i]);
1460 TideCurrentDataSet.clear();
1461 for (
unsigned int i = 0; i < TCDS_temp.size(); i++) {
1462 wxString tide = TCDS_temp[i];
1463 wxFileName ft(tide);
1464 if (ft.FileExists()) TideCurrentDataSet.push_back(TCDS_temp[i]);
1471 g_compatOsVersion =
"";
1472 pConfig->SetPath(
"/Settings");
1473 pConfig->Write(
"CompatOS", g_compatOS);
1474 pConfig->Write(
"CompatOsVersion", g_compatOsVersion);
1478int OCPNPlatform::platformApplyPrivateSettingsString(wxString settings,
1479 ArrayOfCDI *pDirArray) {
1482 ret_val = androidApplySettingsString(settings, pDirArray);
1488void OCPNPlatform::applyExpertMode(
bool mode) {
1492 g_bBasicMenus = !mode;
1500static wxString ExpandPaths(wxString paths,
OCPNPlatform *platform);
1502int OCPNPlatform::DoFileSelectorDialog(wxWindow *parent, wxString *file_spec,
1503 wxString Title, wxString initDir,
1504 wxString suggestedName,
1505 wxString wildcard) {
1507 int result = wxID_CANCEL;
1511 wxString idir = initDir;
1512 if (initDir.StartsWith(
1516 result = androidFileChooser(&file, idir, Title, suggestedName, wildcard);
1517 if (file_spec) *file_spec = file;
1519 long flag = wxFD_DEFAULT_STYLE;
1520 if (suggestedName.Length()) {
1524 wxString mask = wildcard;
1525 if (wxNOT_FOUND != mask.Find(
"gpx")) mask.Prepend(
"GPX files (*.gpx)|");
1527 wxFileDialog *psaveDialog =
1528 new wxFileDialog(parent, Title, initDir, suggestedName, mask, flag);
1536 if (parent) parent->HideWithEffect(wxSHOW_EFFECT_BLEND);
1539 result = psaveDialog->ShowModal();
1542 if (parent) parent->ShowWithEffect(wxSHOW_EFFECT_BLEND);
1545 if (file_spec) *file_spec = psaveDialog->GetPath();
1553int OCPNPlatform::DoDirSelectorDialog(wxWindow *parent, wxString *file_spec,
1554 wxString Title, wxString initDir,
1557 int result = wxID_CANCEL;
1561 wxString idir = initDir;
1562 if (initDir.StartsWith(
1566 result = androidFileChooser(&dir, idir, Title,
"",
"",
true,
1568 if (file_spec) *file_spec = dir;
1570 wxDirDialog *dirSelector =
new wxDirDialog(
1571 parent, Title, initDir, wxDD_DEFAULT_STYLE | wxDD_DIR_MUST_EXIST);
1574 dirSelector->SetFont(*qFont);
1581 if (parent) parent->HideWithEffect(wxSHOW_EFFECT_BLEND);
1584 result = dirSelector->ShowModal();
1587 if (parent) parent->ShowWithEffect(wxSHOW_EFFECT_BLEND);
1590 if (result == wxID_CANCEL) {
1593 *file_spec = dirSelector->GetPath();
1603MyConfig *OCPNPlatform::GetConfigObject() {
1606 result =
new MyConfig(GetConfigFileName());
1615bool OCPNPlatform::hasInternalGPS(wxString profile) {
1617 bool t = androidDeviceHasGPS();
1631void OCPNPlatform::ShowBusySpinner() { AbstractPlatform::ShowBusySpinner(); }
1633void OCPNPlatform::HideBusySpinner() { AbstractPlatform::HideBusySpinner(); }
1635double OCPNPlatform::GetDisplayDensityFactor() {
1637 return getAndroidDisplayDensity();
1643long OCPNPlatform::GetDefaultToolbarOrientation() {
1645 return wxTB_VERTICAL;
1647 return wxTB_VERTICAL;
1651int OCPNPlatform::GetStatusBarFieldCount() {
1657 wxFont *templateFont = FontMgr::Get().
GetFont(_(
"StatusBar"), 0);
1658 dc.SetFont(*templateFont);
1661 dc.GetTextExtent(
"WWWWWW", &width, NULL, NULL, NULL, templateFont);
1662 double font_size_pix = (double)width / 6.0;
1666 double nChars = dispSize.x / font_size_pix;
1676 return kStatFieldCount;
1680double OCPNPlatform::getFontPointsperPixel() {
1681 double pt_per_pixel = 1.0;
1691 if (m_pt_per_pixel == 0) {
1696 12, wxFONTFAMILY_DEFAULT, wxFONTSTYLE_NORMAL, wxFONTWEIGHT_BOLD, FALSE,
1697 wxString(
""), wxFONTENCODING_SYSTEM);
1701 dc.GetTextExtent(
"H", &width, &height, NULL, NULL, f);
1703 if (height > 0) m_pt_per_pixel = 12.0 / (double)height;
1705 if (m_pt_per_pixel > 0) pt_per_pixel = m_pt_per_pixel;
1708 return pt_per_pixel;
1713 return getAndroidDisplayDimensions();
1730 ret = GetAndroidDisplaySize();
1736double OCPNPlatform::GetDisplayAreaCM2() {
1741 ratio = (double)sz.x / (
double)sz.y;
1743 ratio = (double)sz.y / (
double)sz.x;
1745 double area = size1 * (size1 * ratio) / 100.;
1751 if (monitor < m_displaySizeMMOverride.size()) {
1752 m_displaySizeMMOverride[monitor] = sizeMM;
1756double OCPNPlatform::GetDisplayDPmm() {
1758 return getAndroidDPmm();
1765unsigned int OCPNPlatform::GetSelectRadiusPix() {
1766 return GetDisplayDPmm() *
1767 (g_btouch ? g_selection_radius_touch_mm : g_selection_radius_mm);
1770bool OCPNPlatform::GetFullscreen() {
1773 bret = androidGetFullscreen();
1781bool OCPNPlatform::SetFullscreen(
bool bFull) {
1784 bret = androidSetFullscreen(bFull);
1791void OCPNPlatform::PositionAISAlert(wxWindow *alert_window) {
1794 alert_window->SetSize(g_ais_alert_dialog_x, g_ais_alert_dialog_y,
1795 g_ais_alert_dialog_sx, g_ais_alert_dialog_sy);
1799 alert_window->Centre();
1805wxDirDialog *OCPNPlatform::AdjustDirDialogFont(wxWindow *container,
1807 wxDirDialog *ret_dlg = dlg;
1811 dlg->SetSize(container->GetSize());
1814 wxSize sds = dlg->GetSize();
1815 wxSize ss = container->GetSize();
1820 wxString msg = dlg->GetMessage();
1821 wxString default_dir = dlg->GetPath();
1825 ret_dlg =
new wxDirDialog(NULL, msg, default_dir,
1826 wxDD_DEFAULT_STYLE | wxDD_DIR_MUST_EXIST);
1829 wxFont *smallFont =
new wxFont(*dialogFont);
1830 smallFont->SetPointSize((smallFont->GetPointSize() / 2) +
1832 ret_dlg->SetFont(*smallFont);
1834 ret_dlg->SetSize(container->GetSize());
1842wxFileDialog *OCPNPlatform::AdjustFileDialogFont(wxWindow *container,
1843 wxFileDialog *dlg) {
1844 wxFileDialog *ret_dlg = dlg;
1848 dlg->SetSize(container->GetSize());
1851 wxSize sds = dlg->GetSize();
1852 wxSize ss = container->GetSize();
1857 wxString msg = dlg->GetMessage();
1858 wxString default_dir = dlg->GetDirectory();
1859 wxString default_file = dlg->GetFilename();
1860 wxString wildcard = dlg->GetWildcard();
1864 ret_dlg =
new wxFileDialog(NULL, msg, default_dir, default_file, wildcard,
1868 wxFont *smallFont =
new wxFont(*dialogFont);
1869 smallFont->SetPointSize((smallFont->GetPointSize() / 2) +
1871 ret_dlg->SetFont(*smallFont);
1873 ret_dlg->SetSize(container->GetSize());
1881double OCPNPlatform::GetToolbarScaleFactor(
int GUIScaleFactor) {
1889 wxSize style_tool_size(32, 32);
1891 if (g_StyleManager) {
1893 if (style) style_tool_size = style->GetToolSize();
1895 double tool_size = style_tool_size.x;
1901 double premult = 1.0;
1903 double target_size = 9.0;
1905 double basic_tool_size_mm = tool_size / GetDisplayDPmm();
1906 premult = target_size / basic_tool_size_mm;
1909 premult = wxMax(45 * getAndroidDisplayDensity(), 45) /
1915 double postmult = exp(GUIScaleFactor * (log(2.0) / 5.0));
1919 rv = premult * postmult;
1920 rv = wxMin(rv, getAndroidDisplayDensity() *
1924 double premult = 1.0;
1926 if (g_bresponsive) {
1929 wxSize style_tool_size = style->GetToolSize();
1930 double tool_size = style_tool_size.x;
1934 double target_size = 9.0;
1936 double basic_tool_size_mm = tool_size / GetDisplayDPmm();
1937 premult = target_size / basic_tool_size_mm;
1941 double postmult = exp(GUIScaleFactor * (0.693 / 5.0));
1943 rv = premult * postmult;
1944 rv = wxMin(rv, 3.0);
1945 rv = wxMax(rv, 0.5);
1954double OCPNPlatform::GetCompassScaleFactor(
int GUIScaleFactor) {
1961 if (g_bresponsive) {
1964 wxSize style_tool_size = style->GetToolSize();
1965 double compass_size = style_tool_size.x;
1971 double premult = wxMax(28 * getAndroidDisplayDensity(), 50) / compass_size;
1974 double postmult = exp(GUIScaleFactor * (log(2.0) / 5.0));
1977 rv = premult * postmult;
1978 rv = wxMin(rv, getAndroidDisplayDensity() *
1983 double premult = 1.0;
1985 if (g_bresponsive) {
1987 wxSize style_tool_size = style->GetToolSize();
1988 double compass_size = style_tool_size.x;
1991 double target_size = 6.0;
1993 double basic_tool_size_mm = compass_size / GetDisplayDPmm();
1994 premult = target_size / basic_tool_size_mm;
1997 double postmult = exp(GUIScaleFactor * (0.693 / 5.0));
1999 rv = premult * postmult;
2001 rv = wxMin(rv, 3.0);
2002 rv = wxMax(rv, 0.5);
2004#if defined(__WXOSX__) || defined(__WXGTK3__)
2007 if (top_frame::Get()) rv *= top_frame::Get()->GetContentScaleFactor();
2017float OCPNPlatform::GetChartScaleFactorExp(
float scale_linear) {
2018 double factor = 1.0;
2020 factor = exp(scale_linear * (log(3.0) / 5.0));
2025 factor = exp(scale_linear * (0.693 / 5.0));
2029 factor = wxMax(factor, .5);
2030 factor = wxMin(factor, 6.);
2035float OCPNPlatform::GetMarkScaleFactorExp(
float scale_linear) {
2036 if (scale_linear <= 0)
2037 return GetChartScaleFactorExp(scale_linear);
2039 return GetChartScaleFactorExp(scale_linear - 1);
2056bool OCPNPlatform::hasInternalBT(wxString profile) {
2058 bool t = androidDeviceHasBlueTooth();
2067bool OCPNPlatform::startBluetoothScan() {
2069 return androidStartBluetoothScan();
2076bool OCPNPlatform::stopBluetoothScan() {
2078 return androidStopBluetoothScan();
2085wxArrayString OCPNPlatform::getBluetoothScanResults() {
2086 wxArrayString ret_val;
2088 return androidGetBluetoothScanResults();
2091 ret_val.Add(
"line 1");
2092 ret_val.Add(
"line 2");
2093 ret_val.Add(
"line 3");
2103bool OCPNPlatform::AllowAlertDialog(
const wxString &class_name) {
2108 wxWindowList::compatibility_iterator node = wxTopLevelWindows.GetFirst();
2110 wxWindow *win = node->GetData();
2111 if (win->IsShown()) nTLW++;
2113 node = node->GetNext();
2127void OCPNPlatform::setChartTypeMaskSel(
int mask, wxString &indicator) {
2129 return androidSetChartTypeMaskSel(mask, indicator);
2134QString g_qtStyleSheet;
2136bool LoadQtStyleSheet(wxString &sheet_file) {
2137 if (wxFileExists(sheet_file)) {
2140 QString file(sheet_file.c_str());
2142 File.open(QFile::ReadOnly);
2143 g_qtStyleSheet = QLatin1String(File.readAll());
2153QString getQtStyleSheet() {
return g_qtStyleSheet; }
2157bool OCPNPlatform::isPlatformCapable(
int flag) {
2161 if (flag == PLATFORM_CAP_PLUGINS) {
2163 wxString tsdk(android_plat_spc.msdk);
2164 if (tsdk.ToLong(&platver)) {
2165 if (platver >= 11)
return true;
2167 }
else if (flag == PLATFORM_CAP_FASTPAN) {
2169 wxString tsdk(android_plat_spc.msdk);
2170 if (tsdk.ToLong(&platver)) {
2171 if (platver >= 14)
return true;
2179void OCPNPlatform::platformLaunchDefaultBrowser(wxString URL) {
2181 androidLaunchBrowser(URL);
2183 ::wxLaunchDefaultBrowser(URL);
2193EVT_PAINT(OCPNColourPickerCtrl::OnPaint)
2202 const wxColour &initial,
2204 const wxSize &size,
long style,
2205 const wxValidator &validator,
2206 const wxString &name) {
2207 Create(parent,
id, initial, pos, size, style, validator, name);
2210bool OCPNColourPickerCtrl::Create(wxWindow *parent, wxWindowID
id,
2211 const wxColour &col,
const wxPoint &pos,
2212 const wxSize &size,
long style,
2213 const wxValidator &validator,
2214 const wxString &name) {
2215 m_bitmap = wxBitmap(60, 13);
2218 if (!wxBitmapButton::Create(parent,
id, m_bitmap, pos, size,
2219 style | wxBU_AUTODRAW, validator, name)) {
2220 wxFAIL_MSG(
"OCPNColourPickerCtrl creation failed");
2225 Connect(GetId(), wxEVT_BUTTON,
2226 wxCommandEventHandler(OCPNColourPickerCtrl::OnButtonClick), NULL,
2236void OCPNColourPickerCtrl::InitColourData() {
2238 ms_data.SetChooseFull(
true);
2239 unsigned char grey = 0;
2240 for (
int i = 0; i < 16; i++, grey += 16)
2243 wxColour colour(grey, grey, grey);
2244 ms_data.SetCustomColour(i, colour);
2249void OCPNColourPickerCtrl::OnButtonClick(wxCommandEvent &WXUNUSED(ev)) {
2251 unsigned int cco = 0;
2254 cco |= m_colour.Red();
2256 cco |= m_colour.Green();
2258 cco |= m_colour.Blue();
2259 unsigned int cc = androidColorPicker(cco);
2262 unsigned char blue = (
unsigned char)cc % 256;
2263 unsigned char green = (
unsigned char)(cc >> 8) % 256;
2265 unsigned char red = (
unsigned char)(cc >> 16) % 256;
2266 cnew.Set(red, green, blue);
2272 ms_data.SetColour(m_colour);
2275 wxColourDialog dlg(
this, &ms_data);
2276 if (dlg.ShowModal() == wxID_OK) {
2277 ms_data = dlg.GetColourData();
2278 SetColour(ms_data.GetColour());
2283void OCPNColourPickerCtrl::UpdateColour() {
2285 SetBitmapLabel(wxBitmap());
2288 wxMemoryDC dc(m_bitmap);
2289 dc.SetPen(*wxTRANSPARENT_PEN);
2290 dc.SetBrush(wxBrush(m_colour));
2291 dc.DrawRectangle(0, 0, m_bitmap.GetWidth(), m_bitmap.GetHeight());
2293 dc.SelectObject(wxNullBitmap);
2294 SetBitmapLabel(m_bitmap);
2297void OCPNColourPickerCtrl::SetColour(wxColour &c) {
2299 m_bitmap = wxBitmap(GetSize().x - 20, GetSize().y - 20);
2303wxColour OCPNColourPickerCtrl::GetColour() {
return m_colour; }
2305wxSize OCPNColourPickerCtrl::DoGetBestSize()
const {
2306 wxSize sz(wxBitmapButton::DoGetBestSize());
2313 if (HasFlag(wxCLRP_SHOW_LABEL))
return sz;
2321void OCPNColourPickerCtrl::OnPaint(wxPaintEvent &event) {
2324 int offset_x = (GetSize().x - m_bitmap.GetWidth()) / 2;
2325 int offset_y = (GetSize().y - m_bitmap.GetHeight()) / 2;
2327 dc.SetPen(*wxTRANSPARENT_PEN);
2328 dc.SetBrush(wxBrush(m_colour));
2329 dc.DrawRectangle(offset_x, offset_y, m_bitmap.GetWidth(),
2330 m_bitmap.GetHeight());
Select * pSelectAIS
Global instance.
Class AisDecoder and helpers.
Global state for AIS decoder.
wxFont * FindOrCreateFont(int point_size, wxFontFamily family, wxFontStyle style, wxFontWeight weight, bool underline=false, const wxString &facename=wxEmptyString, wxFontEncoding encoding=wxFONTENCODING_DEFAULT)
Creates or finds a matching font in the font cache.
void LoadFontNative(wxString *pConfigString, wxString *pNativeDesc)
Loads font settings from a string descriptor.
wxFont * GetFont(const wxString &TextElement, int requested_font_size=0)
Get a font object for a UI element.
std::string Homedir() const
home directory, convenience stuff.
std::string UserDatadir()
The single, user-writable common parent for plugin data directories, typically ending in 'plugins'.
static PluginPaths * GetInstance()
Return the singleton instance.
int GetErrorCount() const
Return the size of the error message's array.
int Parse(const wxString &doc, wxJSONValue *val)
Parse the JSON document.
The JSON value class implementation.
int Size() const
Return the size of the array or map stored in this value.
bool HasMember(unsigned index) const
Return TRUE if the object contains an element at the specified index.
wxString AsString() const
Return the stored value as a wxWidget's string.
Global variables reflecting command line options and arguments.
bool g_bsmoothpanzoom
Controls how the chart panning and zooming smoothing is done during user interactions.
wxString g_default_font_facename
Default font size for user interface elements such as menus, dialogs, etc.
bool g_bRollover
enable/disable mouse rollover GUI effects
std::vector< size_t > g_config_display_size_mm
Size of pysical screen in millimeters.
Global variables stored in configuration file.
Dump debug info on crash.
Extern C linked utilities.
std::vector< OCPN_MonitorInfo > g_monitor_info
Information about the monitors connected to the system.
void EnumerateMonitors()
Enumerate the monitors connected to the system.
bool g_running
Android only.
OpenGL chart rendering canvas.
wxFont * GetOCPNScaledFont(wxString item, int default_size)
Retrieves a font from FontMgr, optionally scaled for physical readability.
General purpose GUI support.
size_t g_current_monitor
Current monitor displaying main application frame.
Miscellaneous globals primarely used by gui layer, not persisted in configuration file.
GUI constant definitions.
Enhanced logging interface on top of wx/log.h.
MacOS hardware probing functions.
void cache_clear()
Remove all files in cache:
MyConfig * pConfig
Global instance.
Miscellaneous utilities, many of which string related.
options * g_options
Global instance.
Downloaded plugins cache.
Plugin installation and data paths support.
wxString GetWritableDocumentsDir()
Returns the platform-specific default documents directory.
Select * pSelect
Global instance.
Select * pSelectTC
Global instance.
Selected route, segment, waypoint, etc.
Abstract gFrame/MyFrame interface.