Ticket #3: fix_matsys_init.patch

File fix_matsys_init.patch, 18.1 KB (added by Carsten, 2 years ago)

This patch fixes the issue, but should be tested also under Windows before being applied.

  • CaWE/AppCaWE.cpp

     
    3131#include "wx/splash.h" 
    3232#include "wx/stdpaths.h" 
    3333 
    34 #if defined(_WIN32) 
    35 #define WIN32_LEAN_AND_MEAN 
    36 #include <windows.h> 
    37 #include <direct.h> 
    38 #endif 
    39  
    4034#include "AppCaWE.hpp" 
    4135#include "ChildFrameViewWin2D.hpp" 
    4236#include "ChildFrameViewWin3D.hpp" 
     
    5044#include "ToolbarMaterials.hpp" 
    5145#include "Tool.hpp" 
    5246#include "ToolManager.hpp" 
     47 
     48#include "ClipSys/CollisionModelMan_impl.hpp" 
    5349#include "ConsoleCommands/Console.hpp" 
    5450#include "ConsoleCommands/ConsoleStdout.hpp" 
    5551#include "ConsoleCommands/ConsoleInterpreter.hpp" 
     
    5753#include "ConsoleCommands/ConVar.hpp" 
    5854#include "ConsoleCommands/ConFunc.hpp" 
    5955#include "FileSys/FileManImpl.hpp" 
    60 #include "MaterialSystem/MapComposition.hpp" 
    61 #include "MaterialSystem/MaterialManagerImpl.hpp" 
    62 #include "MaterialSystem/Renderer.hpp" 
    63 #include "MaterialSystem/TextureMap.hpp" 
    64 #include "PlatformAux.hpp" 
    6556#include "GuiSys/GuiMan.hpp" 
    66 #include "GuiSys/GuiManImpl.hpp" 
    6757#include "GuiSys/Window.hpp" 
     58#include "MaterialSystem/MaterialManagerImpl.hpp" 
    6859#include "TypeSys.hpp" 
    69 #include "ClipSys/CollisionModelMan_impl.hpp" 
    7060 
    71 #ifdef _WIN32 
    72 #elif __linux__ 
    73 #include <dirent.h> 
    74 #include <dlfcn.h> 
    75 #define __stdcall 
    76 #define GetProcAddress dlsym 
    77 #define FreeLibrary dlclose 
    78 #endif 
    7961 
    80  
    8162static cf::ConsoleStdoutT ConsoleStdout; 
    8263cf::ConsoleI* Console=&ConsoleStdout; 
    8364 
     
    10283AppCaWE::AppCaWE() 
    10384    : wxApp(), 
    10485      m_FileConfig(NULL), 
    105       m_ParentFrame(NULL), 
    106       m_RendererDLL(NULL) 
     86      m_ParentFrame(NULL) 
    10787{ 
    10888    static ConsoleInterpreterImplT ConInterpreterImpl; 
    10989    ConsoleInterpreter=&ConInterpreterImpl; 
     
    232212 
    233213    MaterialManager=&MatManImpl; 
    234214 
    235  
    236     // Prepare the name strings. 
    237 #ifdef SCONS_BUILD_DIR 
    238     #define QUOTE(str) QUOTE_HELPER(str) 
    239     #define QUOTE_HELPER(str) #str 
    240  
    241     #ifdef _WIN32 
    242     const wxString MatSysRendererDLLName=wxString("Libs/")+QUOTE(SCONS_BUILD_DIR)+"/MaterialSystem/RendererOpenGL12.dll"; 
    243     #else 
    244     const wxString MatSysRendererDLLName=wxString("Libs/")+QUOTE(SCONS_BUILD_DIR)+"/MaterialSystem/libRendererOpenGL12.so"; 
    245     #endif 
    246  
    247     #undef QUOTE 
    248     #undef QUOTE_HELPER 
    249 #else 
    250     const wxString MatSysRendererDLLName=wxString("Renderers/RendererOpenGL12")+PlatformAux::GetEnvFileSuffix().c_str()+".dll"; 
    251 #endif 
    252  
    253  
    254     // Load the DLL. 
    255     #ifdef _WIN32 
    256         m_RendererDLL=LoadLibrary(L"./RendererOpenGL12.dll"); 
    257  
    258         if (m_RendererDLL==NULL) 
    259             m_RendererDLL=LoadLibrary(MatSysRendererDLLName); 
    260     #else 
    261         // Note that RTLD_GLOBAL must *not* be passed-in here, or else we get in trouble with subsequently loaded libraries. 
    262         // (E.g. dlsym(RendererDLL, "GetRenderer") return identical results for different RendererDLLs.) 
    263         // Please refer to the man page of dlopen for more details. 
    264         m_RendererDLL=dlopen("./libRendererOpenGL12.so", RTLD_NOW); 
    265         if (!m_RendererDLL) m_RendererDLL=dlopen(MatSysRendererDLLName.c_str(), RTLD_NOW); 
    266  
    267         if (!m_RendererDLL) printf("%s\n", dlerror()); 
    268     #endif 
    269  
    270     if (m_RendererDLL==NULL) { wxMessageBox("FAILED - could not load the library at "+MatSysRendererDLLName, "ERROR"); return false; } 
    271  
    272  
    273     // Get the renderer. 
    274     typedef MatSys::RendererI* (__stdcall *GetRendererT)(cf::ConsoleI* Console_, cf::FileSys::FileManI* FileMan_); 
    275  
    276     #ifdef _WIN32 
    277         GetRendererT GetRenderer=(GetRendererT)GetProcAddress(m_RendererDLL, "_GetRenderer@8"); 
    278     #else 
    279         GetRendererT GetRenderer=(GetRendererT)GetProcAddress(m_RendererDLL, "GetRenderer"); 
    280     #endif 
    281  
    282     if (!GetRenderer) { wxMessageBox("FAILED - could not get the address of the GetRenderer() function.", "ERROR"); FreeLibrary(m_RendererDLL); return false; } 
    283  
    284     // When we get here, the console and the file man must already have been initialized. 
    285     assert(Console!=NULL); 
    286     assert(cf::FileSys::FileMan!=NULL); 
    287     MatSys::Renderer=GetRenderer(Console, cf::FileSys::FileMan); 
    288  
    289     if (MatSys::Renderer==NULL) { wxMessageBox("FAILED - could not get the renderer.", "ERROR"); FreeLibrary(m_RendererDLL); return false; } 
    290  
    291  
    292     // Check if we already have OpenGL errors here. 
    293     // Shouldn't be the case though, because any errors here must have been caused by the ParentFrames wxCanvas ctor. 
    294     GLenum Error=glGetError(); 
    295     if (Error!=GL_NO_ERROR) wxMessageBox(wxString::Format("glGetError() reported error %i!", Error)); 
    296  
    297     if (!MatSys::Renderer->IsSupported()) 
    298     { 
    299         wxMessageBox("Renderer "+MatSysRendererDLLName+" says that it's not supported.\n\n" 
    300                      "(This may be caused by your desktop being set to 16 BPP (or less).\n" 
    301                      "Please set your desktop bit-depth to 32 BPP (True Color), and try again.)"); 
    302         FreeLibrary(m_RendererDLL); 
    303         return false; 
    304     } 
    305  
    306     MatSys::Renderer->Initialize(); 
    307  
    308  
    309     // Get the texture manager. 
    310     typedef MatSys::TextureMapManagerI* (__stdcall *GetTMMT)(); 
    311  
    312     #ifdef _WIN32 
    313         GetTMMT GetTMM=(GetTMMT)GetProcAddress(m_RendererDLL, "_GetTextureMapManager@0"); 
    314     #else 
    315         GetTMMT GetTMM=(GetTMMT)GetProcAddress(m_RendererDLL, "GetTextureMapManager"); 
    316     #endif 
    317  
    318     if (!GetTMM) { wxMessageBox("FAILED - could not get the address of the GetTextureMapManager() function.", "ERROR"); FreeLibrary(m_RendererDLL); return false; } 
    319     MatSys::TextureMapManager=GetTMM(); 
    320     if (MatSys::TextureMapManager==NULL) { wxMessageBox("No TextureMapManager obtained.", "ERROR"); FreeLibrary(m_RendererDLL); return false; } 
    321  
    322215    // Register the material script with the CaWE materials definitions. 
    323216    if (MaterialManager->RegisterMaterialScript(AppDir+"/res/CaWE.cmat", AppDir+"/res/").Size()==0) 
    324217        wxMessageBox("CaWE.cmat not found in \""+AppDir+"\".", "WARNING"); 
    325218 
    326     // Create a very simple lightmap for the materials that need one, and register it with the renderer. 
    327     char Data[]={ 255, 255, 255, 255, 255, 255, 0, 0, 
    328                   255, 255, 255, 255, 255, 255, 0, 0 }; 
    329  
    330     MatSys::Renderer->SetCurrentLightMap(MatSys::TextureMapManager->GetTextureMap2D(Data, 2, 2, 3, true, MapCompositionT(MapCompositionT::Linear, MapCompositionT::Linear))); 
    331     MatSys::Renderer->SetCurrentLightDirMap(NULL);      // The MatSys provides a default for LightDirMaps when NULL is set. 
    332  
    333  
    334219    // Initialize the global options from the CaWE config files. 
    335220    Options.Init(); 
    336221 
     
    338223    wxASSERT(CursorMan==NULL); 
    339224    CursorMan=new CursorManT; 
    340225 
    341     // Initialize the GUI managager. 
    342     // This has to be done after all materials are loaded (during Options initialization) so the GuiManager finds its default material. 
    343     cf::GuiSys::GuiMan=new cf::GuiSys::GuiManImplT(); 
    344  
    345226    return wxApp::OnInit(); 
    346227} 
    347228 
     
    355236    delete m_FileConfig; 
    356237    m_FileConfig=NULL; 
    357238 
    358     // Release the GuiManager BEFORE the renderer. 
    359     delete cf::GuiSys::GuiMan; 
    360     cf::GuiSys::GuiMan=NULL; 
    361  
    362     // Unload the Cafu Material System. 
    363     // Checks for NULL are required to gracefully handle (DLL loading, and other) failures in InitInstance(). 
    364     if (MatSys::Renderer!=NULL && m_RendererDLL) 
    365     { 
    366         MatSys::Renderer->Release(); 
    367         FreeLibrary(m_RendererDLL); 
    368     } 
    369  
    370239    // TODO: delete cf::FileSys::FileMan;   // Shoud have   cf::FileSys::FileMan=new cf::FileSys::FileManImplT;   in OnInit(). 
    371240    cf::FileSys::FileMan=NULL; 
    372241 
  • CaWE/ParentFrame.cpp

     
    3434#include "ModelEditor/ChildFrame.hpp" 
    3535#include "ModelEditor/Document.hpp" 
    3636 
     37#include "ConsoleCommands/Console.hpp" 
     38#include "FileSys/FileManImpl.hpp" 
    3739#include "GuiSys/GuiImpl.hpp"   // Needed to catch InitErrorT if GUI document creation fails. 
     40#include "GuiSys/GuiManImpl.hpp" 
     41#include "MaterialSystem/MapComposition.hpp" 
     42#include "MaterialSystem/Renderer.hpp" 
     43#include "MaterialSystem/TextureMap.hpp" 
    3844#include "TextParser/TextParser.hpp" 
     45#include "PlatformAux.hpp" 
    3946 
    4047#include "wx/wx.h" 
    4148#include "wx/aboutdlg.h" 
     
    4956 
    5057#include <fstream> 
    5158 
     59#ifdef _WIN32 
     60#define WIN32_LEAN_AND_MEAN 
     61#include <windows.h> 
     62#include <direct.h> 
     63#elif __linux__ 
     64#include <dirent.h> 
     65#include <dlfcn.h> 
     66#define __stdcall 
     67#define GetProcAddress dlsym 
     68#define FreeLibrary dlclose 
     69#endif 
    5270 
     71 
    5372BEGIN_EVENT_TABLE(ParentFrameT, wxMDIParentFrame) 
    5473#ifdef __WXGTK__ 
    5574    EVT_SIZE(ParentFrameT::OnSize) 
    5675#endif 
     76    EVT_SHOW(ParentFrameT::OnShow) 
    5777    EVT_CLOSE(ParentFrameT::OnClose) 
    5878    EVT_MENU_RANGE(ID_MENU_FILE_NEW_MAP,  ID_MENU_FILE_EXIT,  ParentFrameT::OnMenuFile) 
    5979    EVT_MENU_RANGE(wxID_FILE1,            wxID_FILE9,         ParentFrameT::OnMenuFile) 
     
    84104    : wxMDIParentFrame(NULL /*parent*/, -1 /*id*/, wxString("Cafu World Editor - ") + __DATE__, wxDefaultPosition, wxDefaultSize, wxDEFAULT_FRAME_STYLE | wxMAXIMIZE), 
    85105#endif 
    86106      m_GLCanvas(NULL), 
    87       m_GLContext(NULL) 
     107      m_GLContext(NULL), 
     108      m_RendererDLL(NULL) 
    88109{ 
    89110    wxMenuBar *item0 = new wxMenuBar; 
    90111 
     
    141162#endif 
    142163 
    143164 
    144     // Create the parent GL canvas. 
    145     m_GLCanvas=new wxGLCanvas(this, -1, OpenGLAttributeList, wxPoint(600, 5), wxSize(10, 10), 0, "ParentGLCanvas"); 
    146  
    147  
    148     Centre(wxBOTH); 
    149     Maximize(true);             // The wxMAXIMIZE frame style does not seem to have any effect for this frame...(?) 
    150     Show(true); 
     165    // Create the parent GL canvas and a GL context. 
     166    m_GLCanvas =new wxGLCanvas(this, -1, OpenGLAttributeList, wxPoint(600, 5), wxSize(10, 10), 0, "ParentGLCanvas"); 
    151167    m_GLContext=new wxGLContext(m_GLCanvas); 
    152     wxASSERT(m_GLContext); 
    153     m_GLCanvas->SetCurrent(*m_GLContext);   // Aha - under X11 this must be *after* Show(true), not before the window is opened! 
    154168 
    155     // The above attribute list can certainly NOT be met on 16 BPP desktops. 
    156     // However, we do not check if the RC of the m_GLCanvas is valid here (it should), 
    157     // as the IsSupported() method of each MatSys Renderer does the same check, too, 
    158     // and I have adjusted the error message appropriately there (see AppCaWE.cpp, 
    159     // the user is told to check whether his desktop is set to 32 BPP if IsSupported() fails). 
    160     // const char* Version=(char const*)glGetString(GL_VERSION);     // Another way to see if the RC is valid: Version!=NULL <==> RC valid. 
    161     // printf("%s (%u): GL_VERSION string is \"%s\".\n", __FILE__, __LINE__, Version==NULL ? "NULL" : Version); 
     169    Maximize();     // The wxMAXIMIZE frame style does not seem to suffice... 
     170    Show(); 
    162171} 
    163172 
    164173 
    165174ParentFrameT::~ParentFrameT() 
    166175{ 
    167176    m_FileHistory.Save(*wxConfigBase::Get()); 
     177 
     178    // Release the GuiManager (BEFORE the renderer). 
     179    if (cf::GuiSys::GuiMan!=NULL) 
     180    { 
     181        delete cf::GuiSys::GuiMan; 
     182        cf::GuiSys::GuiMan=NULL; 
     183    } 
     184 
     185    // Release the Cafu Material System. 
     186    MatSys::TextureMapManager=NULL; 
     187 
     188    if (MatSys::Renderer!=NULL) 
     189    { 
     190        MatSys::Renderer->Release(); 
     191        MatSys::Renderer=NULL; 
     192    } 
     193 
     194    if (m_RendererDLL!=NULL) 
     195    { 
     196        FreeLibrary(m_RendererDLL); 
     197        m_RendererDLL=NULL; 
     198    } 
    168199} 
    169200 
    170201 
     
    205236#endif 
    206237 
    207238 
     239void ParentFrameT::OnShow(wxShowEvent& SE) 
     240{ 
     241    if (SE.IsShown() && m_RendererDLL==NULL) 
     242    { 
     243        wxASSERT(m_GLCanvas->IsShownOnScreen()); 
     244 
     245        // Aha - under X11 this must be *after* Show(true), not before the window is opened! 
     246        m_GLCanvas->SetCurrent(*m_GLContext); 
     247 
     248        // Prepare the name strings. 
     249        #ifdef SCONS_BUILD_DIR 
     250            #define QUOTE(str) QUOTE_HELPER(str) 
     251            #define QUOTE_HELPER(str) #str 
     252 
     253            #ifdef _WIN32 
     254            const wxString MatSysRendererDLLName=wxString("Libs/")+QUOTE(SCONS_BUILD_DIR)+"/MaterialSystem/RendererOpenGL12.dll"; 
     255            #else 
     256            const wxString MatSysRendererDLLName=wxString("Libs/")+QUOTE(SCONS_BUILD_DIR)+"/MaterialSystem/libRendererOpenGL12.so"; 
     257            #endif 
     258 
     259            #undef QUOTE 
     260            #undef QUOTE_HELPER 
     261        #else 
     262            const wxString MatSysRendererDLLName=wxString("Renderers/RendererOpenGL12")+PlatformAux::GetEnvFileSuffix().c_str()+".dll"; 
     263        #endif 
     264 
     265 
     266        // Load the DLL. 
     267        #ifdef _WIN32 
     268            m_RendererDLL=LoadLibrary(L"./RendererOpenGL12.dll"); 
     269 
     270            if (m_RendererDLL==NULL) 
     271                m_RendererDLL=LoadLibrary(MatSysRendererDLLName); 
     272        #else 
     273            // Note that RTLD_GLOBAL must *not* be passed-in here, or else we get in trouble with subsequently loaded libraries. 
     274            // (E.g. dlsym(RendererDLL, "GetRenderer") return identical results for different RendererDLLs.) 
     275            // Please refer to the man page of dlopen for more details. 
     276            m_RendererDLL=dlopen("./libRendererOpenGL12.so", RTLD_NOW); 
     277            if (!m_RendererDLL) m_RendererDLL=dlopen(MatSysRendererDLLName.c_str(), RTLD_NOW); 
     278 
     279            if (!m_RendererDLL) printf("%s\n", dlerror()); 
     280        #endif 
     281 
     282        if (m_RendererDLL==NULL) { wxMessageBox("FAILED - could not load the library at "+MatSysRendererDLLName, "ERROR"); Destroy(); return; } 
     283 
     284 
     285        // Get the renderer. 
     286        typedef MatSys::RendererI* (__stdcall *GetRendererT)(cf::ConsoleI* Console_, cf::FileSys::FileManI* FileMan_); 
     287 
     288        #ifdef _WIN32 
     289            GetRendererT GetRenderer=(GetRendererT)GetProcAddress(m_RendererDLL, "_GetRenderer@8"); 
     290        #else 
     291            GetRendererT GetRenderer=(GetRendererT)GetProcAddress(m_RendererDLL, "GetRenderer"); 
     292        #endif 
     293 
     294        if (!GetRenderer) { wxMessageBox("FAILED - could not get the address of the GetRenderer() function.", "ERROR"); Destroy(); return; } 
     295 
     296        // When we get here, the console and the file man must already have been initialized. 
     297        wxASSERT(Console!=NULL); 
     298        wxASSERT(cf::FileSys::FileMan!=NULL); 
     299        MatSys::Renderer=GetRenderer(Console, cf::FileSys::FileMan); 
     300 
     301        if (MatSys::Renderer==NULL) { wxMessageBox("FAILED - could not get the renderer.", "ERROR"); Destroy(); return; } 
     302 
     303 
     304        // Check if we already have OpenGL errors here. 
     305        // Shouldn't be the case though, because any errors here must have been caused by the ParentFrames wxCanvas ctor. 
     306        GLenum Error=glGetError(); 
     307        if (Error!=GL_NO_ERROR) wxMessageBox(wxString::Format("glGetError() reported error %i!", Error)); 
     308 
     309        if (!MatSys::Renderer->IsSupported()) 
     310        { 
     311            wxMessageBox("Renderer "+MatSysRendererDLLName+" says that it's not supported.\n\n" 
     312                         "This may be caused by your desktop being set to 16 BPP (or less).\n" 
     313                         "Please set your desktop bit-depth to 24 or 32 BPP (True Color), and try again."); 
     314            Destroy(); 
     315            return; 
     316        } 
     317 
     318        MatSys::Renderer->Initialize(); 
     319 
     320 
     321        // Get the texture manager. 
     322        typedef MatSys::TextureMapManagerI* (__stdcall *GetTMMT)(); 
     323 
     324        #ifdef _WIN32 
     325            GetTMMT GetTMM=(GetTMMT)GetProcAddress(m_RendererDLL, "_GetTextureMapManager@0"); 
     326        #else 
     327            GetTMMT GetTMM=(GetTMMT)GetProcAddress(m_RendererDLL, "GetTextureMapManager"); 
     328        #endif 
     329 
     330        if (!GetTMM) { wxMessageBox("FAILED - could not get the address of the GetTextureMapManager() function.", "ERROR"); Destroy(); return; } 
     331        MatSys::TextureMapManager=GetTMM(); 
     332        if (MatSys::TextureMapManager==NULL) { wxMessageBox("No TextureMapManager obtained.", "ERROR"); Destroy(); return; } 
     333 
     334        // Create a very simple lightmap for the materials that need one, and register it with the renderer. 
     335        char Data[]={ 255, 255, 255, 255, 255, 255, 0, 0, 
     336                      255, 255, 255, 255, 255, 255, 0, 0 }; 
     337 
     338        MatSys::Renderer->SetCurrentLightMap(MatSys::TextureMapManager->GetTextureMap2D(Data, 2, 2, 3, true, MapCompositionT(MapCompositionT::Linear, MapCompositionT::Linear))); 
     339        MatSys::Renderer->SetCurrentLightDirMap(NULL);      // The MatSys provides a default for LightDirMaps when NULL is set. 
     340 
     341 
     342        // Initialize the GUI managager. 
     343        // This has to be done after all materials are loaded (AppCaWE::OnInit()) and after the MatSys::Renderer has been initialized, 
     344        // so that the GuiManager finds its default material and can register it for rendering. 
     345        cf::GuiSys::GuiMan=new cf::GuiSys::GuiManImplT(); 
     346    } 
     347} 
     348 
     349 
    208350void ParentFrameT::OnClose(wxCloseEvent& CE) 
    209351{ 
    210352    if (!CE.CanVeto()) 
  • CaWE/AppCaWE.hpp

     
    2626 
    2727#include "wx/wx.h" 
    2828 
    29 #if __linux__ 
    30 #define HMODULE void* 
    31 #endif 
    32  
    33  
    3429class ParentFrameT; 
    3530class wxFileConfig; 
    3631 
     
    5348 
    5449    wxFileConfig* m_FileConfig; 
    5550    ParentFrameT* m_ParentFrame; 
    56     HMODULE       m_RendererDLL; 
    5751}; 
    5852 
    5953 
  • CaWE/ParentFrame.hpp

     
    2828#include "wx/mdi.h" 
    2929#include "Templates/Array.hpp" 
    3030 
     31#if __linux__ 
     32#define HMODULE void* 
     33#endif 
    3134 
     35 
    3236class wxGLCanvas; 
    3337class wxGLContext; 
    3438class wxFileName; 
     
    109113#ifdef __WXGTK__ 
    110114    void OnSize    (wxSizeEvent&    SE); 
    111115#endif 
     116    void OnShow    (wxShowEvent&    SE);    ///< Event handler for "has been shown" events. 
    112117    void OnClose   (wxCloseEvent&   CE);    ///< Event handler for close events, e.g. after a system close button or command or a call to Close(). See wx Window Deletion Overview for more details. 
    113118    void OnMenuFile(wxCommandEvent& CE);    ///< Event handler for File menu events. 
    114119    void OnMenuHelp(wxCommandEvent& CE);    ///< Event handler for Help menu events. 
    115120 
     121    HMODULE m_RendererDLL; 
     122 
    116123    DECLARE_EVENT_TABLE() 
    117124}; 
    118125