Assert bei CFormview nach Aufruf Datei->Neu



  • Ich habe ein SDI-Projekt mit einer CFormView als Basisklasse meiner Ansicht. Diese soll immer maximiert starten. Wenn ich in meiner Anwendung jetzt den Menüpunkt Datei->Neu oder Datei->Öffnen betätige, dann gibts einen Assert in der wingdi in Zeile 1102 (ASSERT(m_hObject == NULL);)

    BOOL CGdiObject::Attach(HGDIOBJ hObject)
    {
    	ASSERT(m_hObject == NULL);      // only attach once, detach on destroy
    	if (hObject == NULL)
    		return FALSE;
    	CHandleMap* pMap = afxMapHGDIOBJ(TRUE); // create map if not exist
    	ASSERT(pMap != NULL);
    	pMap->SetPermanent(m_hObject = hObject, this);
    	return TRUE;
    }
    

    Derzeit zeichnet die View nur eine Bitmap und diverse Buttons auf die Oberfläche. Beim normalen Start und Beenden des Programms läuft alles problemlos durch. Jetzt habe ich mal ein leeres Projekt erstellt. Dort ist mir aufgefallen, dass nach dem Aufruf Datei->Neu das Fenster kleiner gezeichnet wird. Ist dieses Verhalten normal? Ich weiß derzeit nicht, wo ich suchen soll.


  • Mod

    OnInitialUpdate wird in einer SDI Anwednung mehrfach aufgerufen. Dein Initialisierungscode wird mehrfach durchlaufen.

    Schau Dir Deinen Callstack doch an.



  • Danke Martin. Ich muss dazu sagen, dass ich die OnInitialUpdate überschrieben habe, um den Buttons und Edit-Feldern eine andere Schriftfarbe zu geben. Kommentiere ich diesen Code aus, dann macht das keine Probleme. Wie kann ich diese Mehrfachinitialisierung umgehen?



  • Ich möchte meine Frage nochmal konkretisieren. Die OnInitialUpdate() sieht jetzt wie folgt aus:

    void CMyAppView::OnInitialUpdate()
    {
    	CFormView::OnInitialUpdate();
    	GetParentFrame()->RecalcLayout();
    	ResizeParentToFit();
    
    	// TODO: Hier Code zum Erstellen einfügen
    	m_SchriftartButton.CreateFont(10, 0, 0, 0, FW_NORMAL, 0, 0, 0, DEFAULT_CHARSET, OUT_CHARACTER_PRECIS, CLIP_CHARACTER_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_DONTCARE, _T("Verdana"));
    	m_SchriftartRahmen.CreateFont(18, 0, 0, 0, FW_NORMAL, 0, 0, 0, DEFAULT_CHARSET, OUT_CHARACTER_PRECIS, CLIP_CHARACTER_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_DONTCARE, _T("Verdana"));
    	m_SchriftartAnzeige.CreateFont(22, 0, 0, 0, FW_BOLD, 0, 0, 0, DEFAULT_CHARSET, OUT_CHARACTER_PRECIS, CLIP_CHARACTER_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_DONTCARE, _T("Arial"));
    
    	m_ctrlButton1.SetFont(&m_SchriftartButton);
    	m_ctrlButton2.SetFont(&m_SchriftartButton);
    	m_ctrlButton3.SetFont(&m_SchriftartButton);
    	m_ctrlButton4.SetFont(&m_SchriftartButton);
    	m_ctrlButton5.SetFont(&m_SchriftartButton);
    	m_ctrlButton6.SetFont(&m_SchriftartButton);
    	m_ctrlButton7.SetFont(&m_SchriftartButton);
    	m_ctrlButton8.SetFont(&m_SchriftartButton);
    	m_ctrlButton9.SetFont(&m_SchriftartButton);
    	m_ctrlButton10.SetFont(&m_SchriftartButton);
    
    	m_ctrlRahmenButtons.SetFont(&m_SchriftartRahmen);
    	m_ctrlRahmenMesswerte.SetFont(&m_SchriftartRahmen);
    
    	m_ctrlAnzeigeRad_links.SetFont(&m_SchriftartAnzeige);
    	m_ctrlAnzeigeRad_rechts.SetFont(&m_SchriftartAnzeige);
    	m_ctrlAnzeigeRad_Spule.SetFont(&m_SchriftartAnzeige);
    	m_ctrlAnzeige_Gewicht.SetFont(&m_SchriftartAnzeige);
    	m_ctrlAnzeige_Lage.SetFont(&m_SchriftartAnzeige);
    	m_ctrlAnzeige_Winkel.SetFont(&m_SchriftartAnzeige);
    
    	m_SchriftartButton.DeleteObject();
    	m_SchriftartRahmen.DeleteObject();
    	m_SchriftartAnzeige.DeleteObject();
    
    	m_ctrlButton10.EnableWindow(FALSE);
    
    }
    

    Das Einfügen von DeleteObject() hat zumindest gebracht, dass er nicht mehr einen Assert produziert. Allerdings sehen jetzt die Schriften egal was man da bei Größe angibt, irgendwie alle gleich aus. Weiterhin wird das MainWnd nach dem Aufruf von Datei->Ne marginal kleiner gezeichnet.
    Jetzt meine Frage:

    1. Wie kann ich erzwingen, dass das Fenster immer maximiert dargestellt wird?
    2. Wie bekomme ich das Schriftartenproblem in den Griff? Die Vorgehensweise hab ich von codinghelp. Diese gilt aber für Dialoge. Nun weiß ich nicht, ob das so 1:1 für das Formview übertragbar ist.


  • Mod

    Bevor Du die Fonst mit CreateFont erzeugst prüfe doch einfach ob diese bereits erzeugt wurden (m_hObject!=NULL).

    BTW: Du darfst die Objekte nicht zestören solange diese noch in einem Control din sind. Das gibt Leaks.

    OnInitialUpdate wird eben mehrfach aufgerufen. Das ist kein Konstruktor.
    Andere Variante. Lagere die Font Erzeugung in den Konstruktor bzw. (besser) OnCreate aus.
    Dann hast Du solche Probleme nicht.



  • Martin Richter schrieb:

    Bevor Du die Fonst mit CreateFont erzeugst prüfe doch einfach ob diese bereits erzeugt wurden (m_hObject!=NULL).

    BTW: Du darfst die Objekte nicht zestören solange diese noch in einem Control din sind. Das gibt Leaks.

    OnInitialUpdate wird eben mehrfach aufgerufen. Das ist kein Konstruktor.
    Andere Variante. Lagere die Font Erzeugung in den Konstruktor bzw. (besser) OnCreate aus.
    Dann hast Du solche Probleme nicht.

    Vielen Dank für die Hilfe. Hatte das wie gesagt aus einen Beispiel von codeproject übernommen.
    Ich habe jetzt die 3x CreateFont-Anweisungen in die OnCreate übertragen und den Rest so belassen. Damit geht es.
    Dann hatte ich noch das Problem, dass beim Neuladen einer Datei das FormView und damt auch das MainFrame kleiner dargestellt wurden. Ich hab jetzt den Eintrag ResizeParentToFit() aus der OnInitialUpdate() entfernt und habe damit erzielt, dass die alte Größe erhalten bleibt. Gibts weiterhin eine vorgefertigte Möglichkeit, beim Neustart die letzte Datei zu laden oder muss ich das selbst implementieren?


  • Mod

    Das musst Du selber einbauen.


Anmelden zum Antworten