diff --git a/direct/src/plugin/p3dInstance.cxx b/direct/src/plugin/p3dInstance.cxx index 87db3f1edc..87fbf64dee 100644 --- a/direct/src/plugin/p3dInstance.cxx +++ b/direct/src/plugin/p3dInstance.cxx @@ -2830,6 +2830,46 @@ make_splash_window() { nout << "parse failure on bar_height " << bar_height << "\n"; } } + if (_fparams.has_token("font_family")) { + string family = _fparams.lookup_token("font_family"); + _splash_window->set_font_family(family); + } + if (_fparams.has_token("font_size")) { + int size = _fparams.lookup_token_int("font_size"); + _splash_window->set_font_size(size); + } + if (_fparams.has_token("font_style")) { + string style = _fparams.lookup_token("font_style"); + + if (style == "normal") { + _splash_window->set_font_style(P3DSplashWindow::FS_normal); + } else if (style == "oblique") { + _splash_window->set_font_style(P3DSplashWindow::FS_oblique); + } else if (style == "italic") { + _splash_window->set_font_style(P3DSplashWindow::FS_italic); + } else { + nout << "parse_failure on font_style " << style << "\n"; + } + } + if (_fparams.has_token("font_weight")) { + string weight = _fparams.lookup_token("font_weight"); + + if (weight == "normal") { + _splash_window->set_font_weight(400); + } else if (weight == "bold") { + _splash_window->set_font_weight(700); + } else if (weight == "bolder") { + _splash_window->set_font_weight(700); + } else if (weight == "lighter") { + _splash_window->set_font_weight(100); + } else if (weight.size() == 3 && + weight[0] >= '1' && weight[0] <= '9' && + weight[1] == '0' && weight[2] == '0') { + _splash_window->set_font_weight(((int)weight[0] - 48) * 100); + } else { + nout << "parse_failure on font_weight " << weight << "\n"; + } + } _splash_window->set_wparams(_wparams); _splash_window->set_install_label(_install_label); diff --git a/direct/src/plugin/p3dOsxSplashWindow.cxx b/direct/src/plugin/p3dOsxSplashWindow.cxx index 979b35160d..6b979b2a7b 100644 --- a/direct/src/plugin/p3dOsxSplashWindow.cxx +++ b/direct/src/plugin/p3dOsxSplashWindow.cxx @@ -683,7 +683,7 @@ paint_progress_bar(CGContextRef context) { // Choose a suitable font. float text_height = 15.0; - CGContextSelectFont(context, "Helvetica", text_height, kCGEncodingMacRoman); + CGContextSelectFont(context, _font_family.c_str(), text_height, kCGEncodingMacRoman); // Measure the text, for centering. CGContextSetTextPosition(context, 0, 0); diff --git a/direct/src/plugin/p3dSession.cxx b/direct/src/plugin/p3dSession.cxx index da9b30874f..27361a8d85 100644 --- a/direct/src/plugin/p3dSession.cxx +++ b/direct/src/plugin/p3dSession.cxx @@ -100,6 +100,8 @@ void P3DSession:: shutdown() { set_failed(); + int exit_code = 0; + if (_p3dpython_started) { // Tell the process we're going away. TiXmlDocument doc; @@ -139,7 +141,14 @@ shutdown() { nout << "Force-killing python process.\n"; TerminateProcess(_p3dpython_handle, 2); } - + + DWORD dw_exit_code = 0; + if (!GetExitCodeProcess(_p3dpython_handle, &dw_exit_code)) { + nout << "GetExitCodeProcess failed, error: " << GetLastError() << "\n"; + } else { + exit_code = (int)dw_exit_code; + } + CloseHandle(_p3dpython_handle); _p3dpython_handle = INVALID_HANDLE_VALUE; @@ -182,19 +191,15 @@ shutdown() { nout << "Python process has successfully stopped.\n"; if (WIFEXITED(status)) { - int code = WEXITSTATUS(status); - - nout << " exited normally, status = " << code << "\n"; - if (code != 0) { - _exit(code); - } + exit_code = WEXITSTATUS(status); + nout << " exited normally, status = " << exit_code << "\n"; } else if (WIFSIGNALED(status)) { nout << " signalled by " << WTERMSIG(status) << ", core = " << WCOREDUMP(status) << "\n"; // This seems to be a popular shell convention. - _exit(128 + WTERMSIG(status)); + exit_code = 128 + WTERMSIG(status); } else if (WIFSTOPPED(status)) { nout << " stopped by " << WSTOPSIG(status) << "\n"; @@ -220,6 +225,11 @@ shutdown() { // Close the pipe now. _pipe_read.close(); + + // If we had an exit status, pass it on to the runtime process. + if (exit_code != 0) { + _exit(exit_code); + } } //////////////////////////////////////////////////////////////////// diff --git a/direct/src/plugin/p3dSplashWindow.cxx b/direct/src/plugin/p3dSplashWindow.cxx index d9dcd802dd..37960d4499 100644 --- a/direct/src/plugin/p3dSplashWindow.cxx +++ b/direct/src/plugin/p3dSplashWindow.cxx @@ -57,6 +57,10 @@ P3DSplashWindow(P3DInstance *inst, bool make_visible) : _bar_height = 22; _bar_width_ratio = 0.6; _bar_height_ratio = 0.1; + _font_family = "Helvetica"; + _font_size = 12; + _font_style = FS_normal; + _font_weight = FW_normal; _button_width = 0; _button_height = 0; _button_x = 0; @@ -268,6 +272,63 @@ set_bar_height(int height, bool percent) { } } +//////////////////////////////////////////////////////////////////// +// Function: P3DSplashWindow::set_font_family +// Access: Public +// Description: Sets the font family of the text above the loading +// bar. +// +// This may only be set before wparams is set. +//////////////////////////////////////////////////////////////////// +void P3DSplashWindow:: +set_font_family(const string &family) { + nout << "font_family " << family << "\n"; + _font_family = family; +} + +//////////////////////////////////////////////////////////////////// +// Function: P3DSplashWindow::set_font_size +// Access: Public +// Description: Sets the font size in pixels of the text above the +// loading bar. The default value is 12. +// +// This may only be set before wparams is set. +//////////////////////////////////////////////////////////////////// +void P3DSplashWindow:: +set_font_size(int size) { + nout << "font_size " << size << "\n"; + _font_size = size; +} + +//////////////////////////////////////////////////////////////////// +// Function: P3DSplashWindow::set_font_style +// Access: Public +// Description: Sets the font style of the text above the loading +// bar. +// +// This may only be set before wparams is set. +//////////////////////////////////////////////////////////////////// +void P3DSplashWindow:: +set_font_style(FontStyle style) { + nout << "font_style " << style << "\n"; + _font_style = style; +} + +//////////////////////////////////////////////////////////////////// +// Function: P3DSplashWindow::set_font_weight +// Access: Public +// Description: Sets the font weight of the text above the loading +// bar. The default is FW_normal. It should be +// a multiple of 100 in the range 100-900. +// +// This may only be set before wparams is set. +//////////////////////////////////////////////////////////////////// +void P3DSplashWindow:: +set_font_weight(int weight) { + nout << "font_weight " << weight << "\n"; + _font_weight = weight; +} + //////////////////////////////////////////////////////////////////// // Function: P3DSplashWindow::set_install_label // Access: Public, Virtual diff --git a/direct/src/plugin/p3dSplashWindow.h b/direct/src/plugin/p3dSplashWindow.h index edbc02c448..3b98b2cfa1 100644 --- a/direct/src/plugin/p3dSplashWindow.h +++ b/direct/src/plugin/p3dSplashWindow.h @@ -51,6 +51,17 @@ public: IP_button_click, IP_none }; + enum FontStyle { + FS_normal, + FS_italic, + FS_oblique + }; + enum FontWeight { + FW_normal = 400, + FW_medium = 500, + FW_bold = 700, + FW_black = 900 + }; virtual void set_image_filename(const string &image_filename, ImagePlacement image_placement); @@ -62,6 +73,10 @@ public: void set_bar_bottom(int bottom); void set_bar_width(int width, bool percent=false); void set_bar_height(int height, bool percent=false); + void set_font_family(const string &family); + void set_font_size(int size); + void set_font_style(FontStyle style); + void set_font_weight(int weight); virtual void set_install_label(const string &install_label); virtual void set_install_progress(double install_progress, bool is_progress_known, size_t received_data); @@ -119,6 +134,11 @@ private: double _bar_width_ratio, _bar_height_ratio; protected: + string _font_family; + int _font_size; + FontStyle _font_style; + int _font_weight; + // The region of the window for accepting button clicks. int _button_width, _button_height; int _button_x, _button_y; diff --git a/direct/src/plugin/p3dWinSplashWindow.cxx b/direct/src/plugin/p3dWinSplashWindow.cxx index dd3f79662a..eb071711db 100644 --- a/direct/src/plugin/p3dWinSplashWindow.cxx +++ b/direct/src/plugin/p3dWinSplashWindow.cxx @@ -37,6 +37,7 @@ P3DWinSplashWindow(P3DInstance *inst, bool make_visible) : _fg_brush = NULL; _bg_brush = NULL; _bar_brush = NULL; + _bar_bg_brush = NULL; _thread_running = false; _install_progress = 0.0; _progress_known = true; @@ -500,6 +501,7 @@ make_window() { _fg_brush = CreateSolidBrush(RGB(_fgcolor_r, _fgcolor_g, _fgcolor_b)); _bg_brush = CreateSolidBrush(RGB(_bgcolor_r, _bgcolor_g, _bgcolor_b)); _bar_brush = CreateSolidBrush(RGB(_barcolor_r, _barcolor_g, _barcolor_b)); + _bar_bg_brush = CreateSolidBrush(RGB(_bar_bgcolor_r, _bar_bgcolor_g, _bar_bgcolor_b)); } //////////////////////////////////////////////////////////////////// @@ -635,6 +637,10 @@ close_window() { DeleteObject(_bar_brush); _bar_brush = NULL; } + if (_bar_bg_brush != NULL) { + DeleteObject(_bar_bg_brush); + _bar_bg_brush = NULL; + } _background_image.dump_image(); _button_ready_image.dump_image(); @@ -794,7 +800,7 @@ paint_progress_bar(HDC dc) { RECT bar_rect = { bar_x, bar_y, bar_x + bar_width, bar_y + bar_height }; // Clear the entire progress bar to white (or the background color). - FillRect(dc, &bar_rect, _bg_brush); + FillRect(dc, &bar_rect, _bar_bg_brush); // Draw the interior of the progress bar in blue (or the bar color). if (_drawn_progress_known) { @@ -820,7 +826,17 @@ paint_progress_bar(HDC dc) { } // Now draw a black (or foreground) border around the progress bar. - FrameRect(dc, &bar_rect, _fg_brush); + if (_bar_border >= 0) { + RECT border_rect = bar_rect; + + for (int i = 0; i < _bar_border; ++i) { + --border_rect.left; + --border_rect.top; + ++border_rect.right; + ++border_rect.bottom; + FrameRect(dc, &border_rect, _fg_brush); + } + } if (!_drawn_label.empty()) { // Now draw the install_label right above it. @@ -836,7 +852,7 @@ paint_progress_bar(HDC dc) { int text_width = text_size.cx; int text_height = text_size.cy; int text_x = (_win_width - text_width) / 2; - int text_y = bar_y - (int)(text_height * 1.5); + int text_y = bar_y - (int)(text_height * 1.5) - _bar_border; // Clear the rectangle behind the text to white. RECT text_rect = { text_x - 2, text_y - 2, text_x + text_width + 4, text_y + text_height + 4 }; @@ -856,7 +872,7 @@ paint_progress_bar(HDC dc) { // Access: Private // Description: The windows event-processing handler. //////////////////////////////////////////////////////////////////// -LONG P3DWinSplashWindow:: +LRESULT P3DWinSplashWindow:: window_proc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam) { switch (msg) { case WM_DESTROY: @@ -937,7 +953,7 @@ window_proc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam) { // Access: Private, Static // Description: The windows event-processing handler, static version. //////////////////////////////////////////////////////////////////// -LONG P3DWinSplashWindow:: +LRESULT P3DWinSplashWindow:: st_window_proc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam) { LONG_PTR self = GetWindowLongPtr(hwnd, GWLP_USERDATA); if (self == NULL) { diff --git a/direct/src/plugin/p3dWinSplashWindow.h b/direct/src/plugin/p3dWinSplashWindow.h index ca7e04b1cf..9c27f4578e 100644 --- a/direct/src/plugin/p3dWinSplashWindow.h +++ b/direct/src/plugin/p3dWinSplashWindow.h @@ -68,8 +68,8 @@ private: void paint_window(HDC dc); bool paint_image(HDC dc, const WinImageData &image, bool use_alpha); void paint_progress_bar(HDC dc); - LONG window_proc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam); - static LONG WINAPI st_window_proc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam); + LRESULT window_proc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam); + static LRESULT WINAPI st_window_proc(HWND hwnd, UINT msg, WPARAM wparam, LPARAM lparam); private: class WinImageData : public ImageData { @@ -112,6 +112,7 @@ private: HBRUSH _fg_brush; HBRUSH _bg_brush; HBRUSH _bar_brush; + HBRUSH _bar_bg_brush; static bool _registered_window_class; }; diff --git a/direct/src/plugin/p3dX11SplashWindow.cxx b/direct/src/plugin/p3dX11SplashWindow.cxx index 6d3d2919a7..4c41b3ca4c 100644 --- a/direct/src/plugin/p3dX11SplashWindow.cxx +++ b/direct/src/plugin/p3dX11SplashWindow.cxx @@ -25,8 +25,6 @@ #include #include -static const char *xfont_name = "-*-helvetica-medium-r-normal--12-120-*-*-p-*-iso8859-1"; - //////////////////////////////////////////////////////////////////// // Function: P3DX11SplashWindow::Constructor // Access: Public @@ -987,12 +985,77 @@ setup_gc() { return; } - _font = XLoadQueryFont(_display, xfont_name); + char style = 'r'; + if (_font_style == FS_oblique) { + style = 'o'; + } else if (_font_style == FS_italic) { + style = 'i'; + } + + // Determine the order at which to try the various weights. From: + // https://developer.mozilla.org/en-US/docs/Web/CSS/font-weight + const char *const *try_weights; + const int num_weights = 7; + + if (_font_weight > 700) { + static const char *const weights[] = {"black", "bold", "demibold", "semibold", "medium", "regular", "extralight"}; + try_weights = weights; + + } else if (_font_weight > 600) { + static const char *const weights[] = {"bold", "black", "demibold", "semibold", "medium", "regular", "extralight"}; + try_weights = weights; + + } else if (_font_weight > 500) { + static const char *const weights[] = {"demibold", "semibold", "bold", "black", "medium", "regular", "extralight"}; + try_weights = weights; + + } else if (_font_weight == 500) { + static const char *const weights[] = {"medium", "regular", "extralight", "demibold", "semibold", "bold", "black"}; + try_weights = weights; + + } else if (_font_weight >= 400) { + static const char *const weights[] = {"regular", "medium", "extralight", "demibold", "semibold", "bold", "black"}; + try_weights = weights; + + } else { + static const char *const weights[] = {"extralight", "regular", "medium", "demibold", "semibold", "bold", "black"}; + try_weights = weights; + } + + char font_name[1024]; + + // Go through the weights array to find the best matching font. + for (int i = 0; i < num_weights; ++i) { + const char *weight_name = try_weights[i]; + + // Compose the proper pattern for finding the desired font face. + snprintf(font_name, 1024, "-*-%s-%s-%c-normal--%d-*-*-*-*-*-iso8859-1", + _font_family.c_str(), weight_name, style, _font_size); + + _font = XLoadQueryFont(_display, font_name); + if (_font != NULL) { + break; + } + nout << "Font " << font_name << " unavailable.\n"; + + if (style == 'i' || style == 'o') { + // If oblique is not found, try italic, and vice versa. + char style2 = 216 - style; + snprintf(font_name, 1024, "-*-%s-%s-%c-normal--%d-*-*-*-*-*-iso8859-1", + _font_family.c_str(), weight_name, style2, _font_size); + + _font = XLoadQueryFont(_display, font_name); + if (_font != NULL) { + break; + } + nout << "Font " << font_name << " unavailable.\n"; + } + } if (_font != NULL) { - nout << "Loaded font " << xfont_name << "\n"; + nout << "Loaded font " << font_name << "\n"; } else { - nout << "Font " << xfont_name << " unavailable.\n"; + nout << "Using fallback font 6x13.\n"; _font = XLoadQueryFont(_display, "6x13"); }