diff --git a/CMakeLists.txt b/CMakeLists.txt index 7209b8cf..45f6ee2d 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -37,8 +37,8 @@ IF (NOT DEFINED YAMLCPP_ROOT) set (YAMLCPP_ROOT "../../yaml-cpp") ENDIF () -IF (NOT DEFINED WXWIDGETS_ROOT) - set (WXWIDGETS_ROOT "../../wxWidgets") +IF (NOT DEFINED CEF_ROOT) + set (CEF_ROOT "../../cef") ENDIF () set (Boost_USE_STATIC_LIBS ON) @@ -56,12 +56,9 @@ set (LOOT_GUI_SRC ${LOOT_SRC} "${CMAKE_SOURCE_DIR}/src/backend/graph.cpp" "${CMAKE_SOURCE_DIR}/src/backend/network.cpp" # Actual GUI code. - "${CMAKE_SOURCE_DIR}/src/gui/ids.cpp" - "${CMAKE_SOURCE_DIR}/src/gui/main.cpp" - "${CMAKE_SOURCE_DIR}/src/gui/settings.cpp" - "${CMAKE_SOURCE_DIR}/src/gui/editor.cpp" - "${CMAKE_SOURCE_DIR}/src/gui/viewer.cpp" - "${CMAKE_SOURCE_DIR}/src/gui/misc.cpp" + "${CMAKE_SOURCE_DIR}/src/gui/main_win.cpp" + "${CMAKE_SOURCE_DIR}/src/gui/handler.cpp" + "${CMAKE_SOURCE_DIR}/src/gui/app.cpp" "${CMAKE_SOURCE_DIR}/src/resource.rc") set (LOOT_API_SRC ${LOOT_SRC} @@ -75,13 +72,15 @@ include_directories ("${CMAKE_SOURCE_DIR}/src" "${YAMLCPP_ROOT}/include" "${LIBLOADORDER_ROOT}/src" "${LIBGIT2_ROOT}/include" - "${WXWIDGETS_ROOT}/include" + ${CEF_ROOT} ${LIBESPM_ROOT} ${Boost_INCLUDE_DIRS}) link_directories ("${LIBLOADORDER_ROOT}/build" "${LIBGIT2_ROOT}/build" - "${YAMLCPP_ROOT}/build") + "${YAMLCPP_ROOT}/build" + "${CEF_ROOT}/Release" + "${CEF_ROOT}/out/Release/lib") ############################## @@ -100,8 +99,6 @@ ENDIF () # MinGW settings. IF (MINGW) - include_directories("${WXWIDGETS_ROOT}/lib/wx/include/${COMPILER_PREFIX}-msw-unicode-static-3.0") - link_directories("${WXWIDGETS_ROOT}/lib") set (CMAKE_C_FLAGS "-m${PROJECT_ARCH} -O3") set (CMAKE_CXX_FLAGS "-m${PROJECT_ARCH} -O3") set (CMAKE_EXE_LINKER_FLAGS "-static-libstdc++ -static-libgcc -Wl,--subsystem,windows") @@ -125,16 +122,13 @@ IF (MINGW) ws2_32) set (LOOT_GUI_LIBS ${LOOT_LIBS} git2 - wx_mswu_webview-3.0-${COMPILER_PREFIX} - wx_mswu_core-3.0-${COMPILER_PREFIX} - wx_baseu-3.0-${COMPILER_PREFIX} - wx_mswu_adv-3.0-${COMPILER_PREFIX} - wxpng-3.0-${COMPILER_PREFIX} - wxzlib-3.0-${COMPILER_PREFIX} + cef_sandbox + libcef + libcef_dll_wrapper + rpcrt4 + shlwapi comctl32) ELSEIF (MSVC) - include_directories("${WXWIDGETS_ROOT}/lib/vc_lib/mswu") - link_directories("${WXWIDGETS_ROOT}/lib/vc_lib") # Force static C++ runtime linkage. IF (PROJECT_STATIC_RUNTIME) @@ -155,12 +149,11 @@ ELSEIF (MSVC) ws2_32) set (LOOT_GUI_LIBS ${LOOT_LIBS} git2 - wxmsw30u_webview - wxmsw30u_adv - wxmsw30u_core - wxbase30u - wxpng - wxzlib + cef_sandbox + libcef + libcef_dll_wrapper + rpcrt4 + shlwapi comctl32) ENDIF () @@ -176,3 +169,17 @@ target_link_libraries (loot${PROJECT_ARCH} ${Boost_LIBRARIES} ${LOOT_LIBS}) # Build application. add_executable (LOOT ${LOOT_GUI_SRC}) target_link_libraries (LOOT ${Boost_LIBRARIES} ${LOOT_GUI_LIBS}) + +# Copy CEF DLLs. +FOREACH(cef_dll d3dcompiler_43.dll d3dcompiler_46.dll libEGL.dll libGLESv2.dll libcef.dll) + add_custom_command(TARGET LOOT POST_BUILD + COMMAND ${CMAKE_COMMAND} -E copy_if_different + "${CMAKE_SOURCE_DIR}/${CEF_ROOT}/$/${cef_dll}" + $) +ENDFOREACH() + +# Copy CEF resources. +add_custom_command(TARGET LOOT POST_BUILD + COMMAND ${CMAKE_COMMAND} -E copy_directory + "${CMAKE_SOURCE_DIR}/${CEF_ROOT}/Resources" + $) diff --git a/README.md b/README.md index 85a04e80..3b7879ee 100644 --- a/README.md +++ b/README.md @@ -19,10 +19,10 @@ LOOT requires the following libraries (version numbers used in latest developmen * [Alphanum](http://www.davekoelle.com/files/alphanum.hpp) * [Boost](http://www.boost.org) v1.55.0 +* [Chromium Embedded Framework](https://code.google.com/p/chromiumembedded/) branch 1916 * [Libespm](http://github.com/WrinklyNinja/libespm) * [Libgit2](http://libgit2.github.com/) v0.21.0 * [Libloadorder](http://github.com/WrinklyNinja/libloadorder) -* [wxWidgets](http://www.wxwidgets.org) v3.0.1 * [yaml-cpp](http://github.com/WrinklyNinja/yaml-cpp) Alphanum and Libespm do not require any additional setup. The rest of the libraries must be built separately. Instructions for building them and LOOT itself using MSVC or MinGW are given in [docs/BUILD.MSVC.md](docs/BUILD.MSVC.md) and [docs/BUILD.MinGW.md](docs/BUILD.MinGW.md) respectively. diff --git a/docs/BUILD.MSVC.md b/docs/BUILD.MSVC.md index f5e1650b..9108ec1c 100644 --- a/docs/BUILD.MSVC.md +++ b/docs/BUILD.MSVC.md @@ -11,9 +11,9 @@ b2 toolset=msvc threadapi=win32 link=static runtime-link=static variant=release `link`, `runtime-link` and `address-model` can all be modified if shared linking or 64 bit builds are desired. LOOT uses statically-linked Boost libraries by default: to change this, edit [CMakeLists.txt](../CMakeLists.txt). -#### wxWidgets +#### Chromium Embedded Framework -Just build the solution provided by wxWidgets. You may need to change the C/C++ Runtime Library setting in each project to `Multi-threaded (/MT)`. +Most of the required binaries are pre-built, but the libcef_dll_wrapper dynamic library must be built. Just open its project file and build it with the `Release` configuration. #### yaml-cpp @@ -53,11 +53,11 @@ Parameter | Values | Default |Description `PROJECT_STATIC_RUNTIME` | `ON`, `OFF` | `ON` | Whether to link the C++ runtime statically or not. This also affects the Boost libraries used. `PROJECT_ARCH` | `32`, `64` | `32` | Whether to build 32 or 64 bit LOOT binaries. `ALPHANUM_ROOT` | path | `../../alphanum` | Path to the folder containing `alphanum.hpp`. +`CEF_ROOT` | path | `../../cef` | Path to the root of the Chromium Embedded Framework folder. `LIBESPM_ROOT` | path | `../../libespm` | Path to the root of the libespm repository folder. `LIBGIT2_ROOT` | path | `../../libgit2` | Path to the root of the libgit2 repository folder. `LIBLOADORDER_ROOT` | path | `../../libloadorder` | Path to the root of the libloadorder repository folder. `YAMLCPP_ROOT` | path | `../../yaml-cpp` | Path to the root of the yaml-cpp folder. -`WXWIDGETS_ROOT` | path | `../../wxWidgets` | Path to the root of the wxWidgets folder. The default paths given in the table above are relative to LOOT's `CMakeLists.txt`. diff --git a/docs/BUILD.MinGW.md b/docs/BUILD.MinGW.md index b92a3f7c..d3c36aba 100644 --- a/docs/BUILD.MinGW.md +++ b/docs/BUILD.MinGW.md @@ -10,12 +10,9 @@ echo "using gcc : 4.6.3 : i686-w64-mingw32-g++ : i686-w64-mingw32-windres . +*/ + +#include "app.h" +#include "handler.h" + +#include "../backend/globals.h" +#include "../backend/helpers.h" + +#include +#include + +namespace loot { + + LootApp::LootApp() {} + + CefRefPtr LootApp::GetBrowserProcessHandler() { + return this; + } + + void LootApp::OnContextInitialized() { + //Make sure this is running in the UI thread. + assert(CefCurrentlyOn(TID_UI)); + + // Information used when creating the native window. + CefWindowInfo window_info; + +#if _WIN32 || _WIN64 + // On Windows we need to specify certain flags that will be passed to CreateWindowEx(). + window_info.SetAsPopup(NULL, "LOOT"); +#endif + + // Set the handler for browser-level callbacks. + CefRefPtr handler(new LootHandler()); + + // Specify CEF browser settings here. + CefBrowserSettings browser_settings; + + // Set URL to load. Ignore any command line values. + std::string url = ToFileURL(g_path_report); + + // Create the first browser window. + CefBrowserHost::CreateBrowser(window_info, handler.get(), url, browser_settings, NULL); + } + +} \ No newline at end of file diff --git a/src/gui/app.h b/src/gui/app.h new file mode 100644 index 00000000..73329660 --- /dev/null +++ b/src/gui/app.h @@ -0,0 +1,47 @@ +/* LOOT + + A load order optimisation tool for Oblivion, Skyrim, Fallout 3 and + Fallout: New Vegas. + + Copyright (C) 2014 WrinklyNinja + + This file is part of LOOT. + + LOOT is free software: you can redistribute + it and/or modify it under the terms of the GNU General Public License + as published by the Free Software Foundation, either version 3 of + the License, or (at your option) any later version. + + LOOT is distributed in the hope that it will + be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with LOOT. If not, see + . +*/ + +#ifndef __LOOT_GUI_APP__ +#define __LOOT_GUI_APP__ + +#include + +namespace loot { + + class LootApp : public CefApp, public CefBrowserProcessHandler { + public: + LootApp(); + + // Override CefApp methods. + virtual CefRefPtr GetBrowserProcessHandler() OVERRIDE; + + // Override CefBrowserProcessHandler methods. + virtual void OnContextInitialized() OVERRIDE; + private: + IMPLEMENT_REFCOUNTING(LootApp); + }; + +} + +#endif \ No newline at end of file diff --git a/src/gui/handler.cpp b/src/gui/handler.cpp new file mode 100644 index 00000000..ab141087 --- /dev/null +++ b/src/gui/handler.cpp @@ -0,0 +1,166 @@ +/* LOOT + + A load order optimisation tool for Oblivion, Skyrim, Fallout 3 and + Fallout: New Vegas. + + Copyright (C) 2014 WrinklyNinja + + This file is part of LOOT. + + LOOT is free software: you can redistribute + it and/or modify it under the terms of the GNU General Public License + as published by the Free Software Foundation, either version 3 of + the License, or (at your option) any later version. + + LOOT is distributed in the hope that it will + be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with LOOT. If not, see + . +*/ + +#include "handler.h" + +#include +#include +#include + +#include +#include +#include + +namespace loot { + + namespace { + LootHandler * g_instance = NULL; + } + + LootHandler::LootHandler() : is_closing_(false) { + assert(!g_instance); + g_instance = this; + } + + LootHandler::~LootHandler() { + g_instance = NULL; + } + + LootHandler* LootHandler::GetInstance() { + return g_instance; + } + + // CefClient methods + //------------------ + + CefRefPtr LootHandler::GetDisplayHandler() { + return this; + } + + CefRefPtr LootHandler::GetLifeSpanHandler() { + return this; + } + + CefRefPtr LootHandler::GetLoadHandler() { + return this; + } + + // CefDisplayHandler methods + //-------------------------- + +#if _WIN32 || _WIN64 + void LootHandler::OnTitleChange(CefRefPtr browser, + const CefString& title) { + assert(CefCurrentlyOn(TID_UI)); + + CefWindowHandle hwnd = browser->GetHost()->GetWindowHandle(); + SetWindowText(hwnd, std::wstring(title).c_str()); + } +#endif + + // CefLifeSpanHandler methods + //--------------------------- + + void LootHandler::OnAfterCreated(CefRefPtr browser) { + assert(CefCurrentlyOn(TID_UI)); + + // Add to the list of existing browsers. + browser_list_.push_back(browser); + } + + bool LootHandler::DoClose(CefRefPtr browser) { + assert(CefCurrentlyOn(TID_UI)); + + // Closing the main window requires special handling. See the DoClose() + // documentation in the CEF header for a detailed destription of this + // process. + if (browser_list_.size() == 1) { + // Set a flag to indicate that the window close should be allowed. + is_closing_ = true; + } + + // Allow the close. For windowed browsers this will result in the OS close + // event being sent. + return false; + } + + void LootHandler::OnBeforeClose(CefRefPtr browser) { + assert(CefCurrentlyOn(TID_UI)); + + // Remove from the list of existing browsers. + for (BrowserList::iterator bit = browser_list_.begin(); bit != browser_list_.end(); ++bit) { + if ((*bit)->IsSame(browser)) { + browser_list_.erase(bit); + break; + } + } + + if (browser_list_.empty()) { + // All browser windows have closed. Quit the application message loop. + CefQuitMessageLoop(); + } + } + + // CefLoadHandler methods + //----------------------- + + void LootHandler::OnLoadError(CefRefPtr browser, + CefRefPtr frame, + ErrorCode errorCode, + const CefString& errorText, + const CefString& failedUrl) { + assert(CefCurrentlyOn(TID_UI)); + + // Don't display an error for downloaded files. + if (errorCode == ERR_ABORTED) + return; + + // Display a load error message. + std::stringstream ss; + ss << "" + << "

Failed to load URL " << std::string(failedUrl) + << " with error " << std::string(errorText) << " (" << errorCode + << ").

"; + + frame->LoadString(ss.str(), failedUrl); + } + + void LootHandler::CloseAllBrowsers(bool force_close) { + + if (!CefCurrentlyOn(TID_UI)) { + // Execute on the UI thread. + CefPostTask(TID_UI, + NewCefRunnableMethod(this, &LootHandler::CloseAllBrowsers, force_close)); + return; + } + + if (browser_list_.empty()) + return; + + for (BrowserList::const_iterator it = browser_list_.begin(); it != browser_list_.end(); ++it) { + (*it)->GetHost()->CloseBrowser(force_close); + } + } + +} \ No newline at end of file diff --git a/src/gui/handler.h b/src/gui/handler.h new file mode 100644 index 00000000..dc029f8e --- /dev/null +++ b/src/gui/handler.h @@ -0,0 +1,87 @@ +/* LOOT + + A load order optimisation tool for Oblivion, Skyrim, Fallout 3 and + Fallout: New Vegas. + + Copyright (C) 2014 WrinklyNinja + + This file is part of LOOT. + + LOOT is free software: you can redistribute + it and/or modify it under the terms of the GNU General Public License + as published by the Free Software Foundation, either version 3 of + the License, or (at your option) any later version. + + LOOT is distributed in the hope that it will + be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with LOOT. If not, see + . +*/ + +#ifndef __LOOT_GUI_HANDLER__ +#define __LOOT_GUI_HANDLER__ + +#include + +#include + +namespace loot { + + class LootHandler : public CefClient, + public CefDisplayHandler, + public CefLifeSpanHandler, + public CefLoadHandler { + public: + LootHandler(); + ~LootHandler(); + + // Provide access to the single global instance of this object. + static LootHandler * GetInstance(); + + // CefClient methods + //------------------ + virtual CefRefPtr GetDisplayHandler() OVERRIDE; + virtual CefRefPtr GetLifeSpanHandler() OVERRIDE; + virtual CefRefPtr GetLoadHandler() OVERRIDE; + + // CefDisplayHandler methods + //-------------------------- + virtual void OnTitleChange(CefRefPtr browser, + const CefString& title) OVERRIDE; + + // CefLifeSpanHandler methods + //--------------------------- + virtual void OnAfterCreated(CefRefPtr browser) OVERRIDE; + virtual bool DoClose(CefRefPtr browser) OVERRIDE; + virtual void OnBeforeClose(CefRefPtr browser) OVERRIDE; + + // CefLoadHandler methods + //----------------------- + virtual void OnLoadError(CefRefPtr browser, + CefRefPtr frame, + ErrorCode errorCode, + const CefString& errorText, + const CefString& failedUrl) OVERRIDE; + + // Request that all existing browser windows close. + void CloseAllBrowsers(bool force_close); + + bool IsClosing() const { return is_closing_; } + + private: + // List of existing browser windows. Only accessed on the CEF UI thread. + typedef std::list > BrowserList; + BrowserList browser_list_; + + bool is_closing_; + + // Include the default reference counting implementation. + IMPLEMENT_REFCOUNTING(LootHandler); + }; +} + +#endif \ No newline at end of file diff --git a/src/gui/main_win.cpp b/src/gui/main_win.cpp new file mode 100644 index 00000000..b9ac858e --- /dev/null +++ b/src/gui/main_win.cpp @@ -0,0 +1,65 @@ +/* LOOT + + A load order optimisation tool for Oblivion, Skyrim, Fallout 3 and + Fallout: New Vegas. + + Copyright (C) 2014 WrinklyNinja + + This file is part of LOOT. + + LOOT is free software: you can redistribute + it and/or modify it under the terms of the GNU General Public License + as published by the Free Software Foundation, either version 3 of + the License, or (at your option) any later version. + + LOOT is distributed in the hope that it will + be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with LOOT. If not, see + . +*/ + +#include "app.h" + +#include +#include + +int APIENTRY wWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPTSTR lpCmdLine, int nCmdShow) { + + // First do all the standard CEF setup stuff. + //---------------------------- + + // Set up CEF sandbox. + CefScopedSandboxInfo scoped_sandbox; + void * sandbox_info = scoped_sandbox.sandbox_info(); + + // Read command line arguments. + CefMainArgs main_args(hInstance); + + // Create the process reference. + CefRefPtr app(new loot::LootApp); + + // Run the process. + int exit_code = CefExecuteProcess(main_args, app.get(), sandbox_info); + if (exit_code >= 0) { + // The sub-process has completed so return here. + return exit_code; + } + + // Initialise CEF settings. + CefSettings settings; + + // Initialize CEF. + CefInitialize(main_args, settings, app.get(), sandbox_info); + + // Run the CEF message loop. This will block until CefQuitMessageLoop() is called. + CefRunMessageLoop(); + + // Shut down CEF. + CefShutdown(); + + return 0; +} \ No newline at end of file diff --git a/src/resource.rc b/src/resource.rc index 530ff093..ab100b2e 100644 --- a/src/resource.rc +++ b/src/resource.rc @@ -1,4 +1,4 @@ -#include "wx/msw/wx.rc" +#include 1 VERSIONINFO FILEVERSION 0,6,0,0 PRODUCTVERSION 0,6,0,0