tutorials.de Buch-Aktion 05/2012
Like Tree1Danke
  • 1 Beitrag von sheel
ERLEDIGT
JA
ANTWORTEN
10
ZUGRIFFE
1087
EMPFEHLEN
  • An Twitter übertragen
  • An Facebook übertragen
AUF DIESES THEMA
ANTWORTEN
  1. #1
    Lexx84 Lexx84 ist offline Mitglied
    Registriert seit
    Dec 2010
    Beiträge
    12
    Hallo,
    ich habe ein MFC-Projekt, das ich in VS2008 als statische Lib erstellt habe.
    Diese Lib habe ich (nach einigen Linker-Errors) auch in mein C++ - Projekt einbinden können.
    Jetzt zu meiner Frage: Ist es möglich, aus dem C++ - Projekt heraus ein komplettes MFC-Projekt zu starten? Und wenn ja, wie? Einen klassischen Startpunkt wie main() hat MFC ja nicht. Ich habe es schon auf diverse Arten versucht (InitInstance(); Hauptdialog.doModal() ) ... aber jedesmal bringt er mir Assertion - Fehler da ich wohl das Projekt nicht richtig starte.
    Vielleicht kann mir hier jemand helfen?
    Falls diese Infos noch nicht ausreichen, kann ich auch noch etwas Code posten
    Vielen Dank
     

  2. #2
    Avatar von sheel
    sheel sheel ist gerade online Moderator
    tutorials.de Moderator
    Registriert seit
    Jul 2007
    Beiträge
    4.506
    Du könntest auch einmal die Fehlermeldung posten.

    MFC hat übrigens auch ein main (WinMain), das allerdings schon vorgefertigt ist, nicht in deinem Quelltext steht und über Umwege InitInstance etc aufruft.
    Geändert von sheel (13.12.10 um 09:37 Uhr) Grund: Tippfehler
     

  3. #3
    Lexx84 Lexx84 ist offline Mitglied
    Registriert seit
    Dec 2010
    Beiträge
    12
    Gut, dann zähl ich mal meine Versuche und die dazugehörigen Fehlermeldungen auf.

    1. Versuch
    Im C++ Projekt direkt versuchen das MFC-Projekt aufzurufen

    C++:
    Code :
    1
    2
    3
    4
    5
    6
    
    void main()
    {
        CWinApp* App = new CWinApp();
        App = AfxGetApp();
        App->InitInstance();
    }

    Kommt zwar keine Fehlermeldung, aber App ist leer (Meldung: Schlechtes Pointing), von daher kommen auch keine MFC-Fenster.

    2. Versuch
    Versuchen AfxGetApp im MFC-Projekt zu bekommen:

    Code :
    1
    2
    3
    4
    5
    6
    
    void main()
    {
        CWinApp* App = new CWinApp();
        CTabExample1App::GetTheApp(App);
        App->InitInstance();
    }

    Wobei CTabExample1App mein MFC-Projekt ist.
    Innerhalb des MFC Projektes sieht das dann so aus:

    Code :
    1
    2
    3
    4
    
    void CTabExample1App::GetTheApp(CWinApp* App)
    {
        App = AfxGetApp();
    }

    Wenn ich nun die Zeile
    Code :
    1
    
    App->InitInstance();
    ausführen lasse kommt ein Debug Assertion Fehler in appcore.cpp in der Zeile
    Code :
    1
    
    ASSERT(AfxGetThread() == NULL);

    Kann mir jemand helfen, CWinApp richtig aufzurufen?
    Vielen Dank
     

  4. #4
    Avatar von sheel
    sheel sheel ist gerade online Moderator
    tutorials.de Moderator
    Registriert seit
    Jul 2007
    Beiträge
    4.506
    Moment, ich such mal Code...

    Also erstens bist du mit main und einem Konsolenprojekt bei MFC falsch.

    Mach eine Win32-Anwendung (oder wie es auch immer heißt).

    Das generierte main sollte jedenfalls WinMain heißen.

    Die Standardmethode zum MFC-Starten sieht dann wie folgt aus:

    Code cpp:
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    
    ASSERT(hPrevInstance == NULL);
     
        int nReturnCode = -1;
        CWinThread* pThread = AfxGetThread();
        CWinApp* pApp = AfxGetApp();
     
        // AFX internal initialization
        if (!AfxWinInit(hInstance, hPrevInstance, lpCmdLine, nCmdShow))
            goto InitFailure;
     
        // App global initializations (rare)
        if (pApp != NULL && !pApp->InitApplication())
            goto InitFailure;
     
        // Perform specific initializations
        if (!pThread->InitInstance())
        {
            if (pThread->m_pMainWnd != NULL)
            {
                TRACE0("Warning: Destroying non-NULL m_pMainWnd\n");
                pThread->m_pMainWnd->DestroyWindow();
            }
            nReturnCode = pThread->ExitInstance();
            goto InitFailure;
        }
        nReturnCode = pThread->Run();
     
    InitFailure:
    #ifdef _DEBUG
        // Check for missing AfxLockTempMap calls
        if (AfxGetModuleThreadState()->m_nTempMapLock != 0)
        {
            TRACE1("Warning: Temp map lock count non-zero (%ld).\n",
                AfxGetModuleThreadState()->m_nTempMapLock);
        }
        AfxLockTempMaps();
        AfxUnlockTempMaps(-1);
    #endif
     
        AfxWinTerm();
        return nReturnCode;
    Geändert von sheel (13.12.10 um 09:49 Uhr)
    Lexx84 bedankt sich. 

  5. #5
    Lexx84 Lexx84 ist offline Mitglied
    Registriert seit
    Dec 2010
    Beiträge
    12
    Vielen Dank für die prompte Hilfe sheel!
    Ich werd es gleich mal ausprobieren!
    Danke nochmals!
     

  6. #6
    Lexx84 Lexx84 ist offline Mitglied
    Registriert seit
    Dec 2010
    Beiträge
    12
    So, ich hab das jetzt mal nach sheel´s Vorgaben eingebaut, hab aber nur einen Teilerfolg verbuchen können. Meine neu erstellte WinMain sieht jetzt folgendermaßen aus:
    Code :
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    
    //WinMain
    int APIENTRY _tWinMain(HINSTANCE hInstance,
                         HINSTANCE hPrevInstance,
                         LPTSTR    lpCmdLine,
                         int       nCmdShow)
    {
       UNREFERENCED_PARAMETER(hPrevInstance);
       UNREFERENCED_PARAMETER(lpCmdLine);
     
        // TODO: Hier Code einfügen.
     
        ASSERT(hPrevInstance == NULL);
     
        int nReturnCode = -1;
        CWinThread* pThread = AfxGetThread();
        CWinApp* pApp = AfxGetApp();
        CTabExample1App::GetTheApp(pApp, pThread);
     
        // AFX internal initialization
        if (!AfxWinInit(hInstance, hPrevInstance, lpCmdLine, nCmdShow))
            goto InitFailure;
     
        // App global initializations (rare)
        if (pApp != NULL && !pApp->InitApplication())
            goto InitFailure;
     
        // Perform specific initializations
        if (!pThread->InitInstance())
        {
            if (pThread->m_pMainWnd != NULL)
            {
                TRACE0("Warning: Destroying non-NULL m_pMainWnd\n");
                pThread->m_pMainWnd->DestroyWindow();
            }
            nReturnCode = pThread->ExitInstance();
            goto InitFailure;
        }
        nReturnCode = pThread->Run();
    }
     
    //In MFC:
    void CTabExample1App::GetTheApp(CWinApp* pApp, CWinThread* pThread)
    {
        pThread = AfxGetThread();
        pApp = AfxGetApp();
    }
    Jetzt habe ich das Problem, dass in Zeile 32 (in der pThread->pMainWnd->DestroyWindow(); aufgerufen wird) folgende Fehlermeldung kommt:
    Code :
    1
    
    0xC0000005: Zugriffsverletzung beim Lesen an Position 0xcccccd34.
    Kommentiere ich diese Zeile aus, läuft der Compiler durch ohne das MFC-Projekt zu starten. Was mache ich falsch?
     

  7. #7
    Avatar von sheel
    sheel sheel ist gerade online Moderator
    tutorials.de Moderator
    Registriert seit
    Jul 2007
    Beiträge
    4.506
    Ungültiger Pointer.

    Statt den goto´s solltest du einmal irgendwelche Dinge einbauen, die sich bemerkbar machen, wenn du schon kein InitFailure drin hast. Und dann schauen, wo er sich aufregt.
     

  8. #8
    Lexx84 Lexx84 ist offline Mitglied
    Registriert seit
    Dec 2010
    Beiträge
    12
    Das InitFailure: hab ich schon drinnen, hab nur vergessen es in den Code meines Post´s mit reinzunehmen Sorry!
    Die AfxWinInit und die pApp-Prüfungen werden ohne InitFailure-Aufruf durchlaufen, nur mit dem pThread scheint er Probleme zu haben...
    Wenn ich an der DestroyWindow() - Zeile anhalte, sieht man folgendes:
    Code :
    1
    
    pThread->m_pMainWnd = 0x0012fce4 {CWnd hWnd=0x00000000}
     

  9. #9
    Rdf42 Tutorials.de Gastzugang
    Ich bin der Meinung, du solltest den Aufruf nicht selber schreiben, sondern das die MFC machen lassen. Im Grunde sollte es reichen, CWinApp zu instanziieren, dann läuft die Schoße von allein ab.
     

  10. #10
    Lexx84 Lexx84 ist offline Mitglied
    Registriert seit
    Dec 2010
    Beiträge
    12
    Ok, hab jetzt auch diesen Ansatz ausprobiert, geht aber nicht.
    Ich bekomme zwei Assertion-Fehler:
    Code :
    1
    
    ASSERT(AfxGetThread() == NULL);
    und wenn ich weiterlaufen lasse (also nicht wiederholen) dann kommt noch
    Code :
    1
    
    ASSERT(afxCurrentWinApp == NULL); // only one CWinApp object please
    Von daher kann ich ja gar kein CWinApp - Objekt instanziieren, da die Beschränkung auf ein Objekt besteht.
    Desweiteren bin ich jetzt verwirrt, welcher Weg führt denn nun zum Ziel?
    Vielleicht hat das schon mal jemand gemacht und kann mir sagen, wie es funktioniert?
    Bin für jede Hilfe dankbar.
     

  11. #11
    Lexx84 Lexx84 ist offline Mitglied
    Registriert seit
    Dec 2010
    Beiträge
    12
    Nach langem ausprobieren, hab ich das Problem nun gelöst.
    Rdf42, du hattest recht, der Aufruf von InitInstance() hat genügt.
    ABER:
    In einer statischen Lib eines MFC Programms sind keine Dialog- bzw. Bildresourcen inkludiert!
    Heißt wenn man seine GUI von außen aufrufen möchte, muss man alle Bitmaps, Icons, Dialoge, halt alles was in der *.rc -Datei ist in den Ordner des C++ Projektes kopieren, dann klappts auch mit der MFC
    Danke an alle, die mir hier geholfen haben!
     

Ähnliche Themen

  1. SQL-DIalog: Export Results->xls aufrufen?
    Von mats_MF im Forum C/C++
    Antworten: 1
    Letzter Beitrag: 26.05.08, 12:54
  2. Antworten: 1
    Letzter Beitrag: 28.11.07, 17:12
  3. PageSetup Dialog in Powerpoint in Makro aufrufen
    Von eagle im Forum Office-Anwendungen
    Antworten: 0
    Letzter Beitrag: 24.11.05, 11:08
  4. Dialog aufrufen über menüpunkt
    Von bukem im Forum VisualStudio & MFC
    Antworten: 4
    Letzter Beitrag: 25.10.04, 13:03
  5. SWT/JFace: Nicht-modaler Dialog von ApplicationWindow aufrufen
    Von chrizzle im Forum Swing, Java2D/3D, SWT, JFace
    Antworten: 0
    Letzter Beitrag: 02.07.04, 09:17