// Shape.cpp: implementation of the CShape class and drived classes. // ////////////////////////////////////////////////////////////////////// #include "stdafx.h" #include "Shape.h" #include #pragma warning( disable : 4996 ) // disable sprintf warning // Dieses Makro changeflag holt aus der Variable "var" // das flag "extract" heraus und fuegt dafuer das flag "insert" ein. #define __changeflag(var, extract, insert) if (var & extract) { \ var ^= extract; \ var |= insert; \ }; ////////////////////////////////////////////////////////////////////// // CShape Class CShape::CShape(short x, short y, COLORREF crColor) { // Initialisieren der Member-Variablen m_x = x; m_y = y; m_crColor = crColor; } ////////////////////////////////////////////////////////////////////// // CFill Class CFill::CFill(short x, short y, COLORREF crFillColor, COLORREF crBorderColor) : CShape(x, y, crBorderColor) { m_crFillColor = crFillColor; }; void CFill::Draw(CDC* pDC) { CBrush brush(m_crFillColor); // Erstellen... pDC->SelectObject(&brush); // ...und auswaehlen ein GDI brushes pDC->FloodFill(m_x, m_y, m_crColor);// Fuellen... brush.DeleteObject(); // und Brush loeschen. }; ////////////////////////////////////////////////////////////////////// // CLineTo Class void CLineTo::Draw(CDC* pDC) { CPen pen; // Konstruieren, dann Initialisieren if( pen.CreatePen( PS_SOLID, 1, m_crColor ) ) { // Auswahl des Objekts im Gerätekontext // Gleichzeitiges Speichern des alten Stifts CPen* pOldPen = pDC->SelectObject( &pen ); // Zeichnen mit dem Stift pDC->LineTo(m_x, m_y); // Ziehen einer Linie... // Wiederherstellen des alten Stifts im Gerätekontext pDC->SelectObject( pOldPen ); } else { // Den Benutzer alarmieren, daß die Ressourcen knapp werden } /* CPen pen(PS_SOLID, 1, m_crColor); // Generieren eines Zeichenstiftes... pDC->SelectObject(&pen); // ...und auswaehlen dieses Stiftes. pDC->LineTo(m_x, m_y); // Ziehen einer Linie... */ // pen.DeleteObject(); // ...und anschliessendes Loeschen des ausgewaehlten Siftes. } ////////////////////////////////////////////////////////////////////// // CLine Class CLine::CLine(short x1, short y1, short x2, short y2, UINT crColor) : CLineTo(x1, y1, crColor) { m_point = CPoint(x2, y2); } void CLine::Draw(CDC* pDC) { POINT currentpos; currentpos = pDC->GetCurrentPosition(); // Ermitteln der aktuellen Cursorposition. pDC->MoveTo(m_point); // Bewegen des Cursors zum Zielpunkt, ... CLineTo::Draw(pDC); // ...zeichnen der Linie und... pDC->MoveTo(currentpos); // ...rueckkehren zum Ausgangspunkt. } ////////////////////////////////////////////////////////////////////// // CRectangle Class CRectangle::CRectangle(RECT rect, COLORREF crFrame, COLORREF crFill) : CShape(NULL, NULL, crFrame) { m_rect = rect; m_crFill = crFill; } void CRectangle::Draw(CDC* pDC) { if (m_crFill == -1) { // Ein durchsichtiges Rechteck zeichnen. CBrush brush(m_crColor); // Erstellen eines graphics device interface (GDI) brushes... pDC->SelectObject(&brush); // ...und auswaehlen des GDI brushes. pDC->FrameRect(&m_rect, &brush); // Zeichnen... brush.DeleteObject(); // ..und brush loeschen. } else { // Ein ausgefuelltes Rechteck zeichnen. CPen pen(PS_SOLID, 1, m_crColor); // Zeichenstift fuer den Rand. pDC->SelectObject(&pen); CBrush brush(m_crFill); // Brush fuer die ausgefuellte Flaeche. pDC->SelectObject(&brush); pDC->Rectangle(&m_rect); brush.DeleteObject(); pen.DeleteObject(); }; } ////////////////////////////////////////////////////////////////////// // CEllipse Class CEllipse::CEllipse(RECT rect, COLORREF crFrame, COLORREF crFill) : CShape(NULL, NULL, crFrame) { m_rect = rect; m_zoomrect = rect; m_crFill = crFill; } void CEllipse::Draw(CDC* pDC) { CBrush brush; CPen pen(PS_SOLID, 1, m_crColor); pDC->SelectObject(&pen); if (m_crFill == -1) // Eine transparente Ellipse zeichnen. brush.CreateStockObject(NULL_BRUSH); else // Eine ausgefuellte Ellipse zeichnen. brush.CreateSolidBrush(m_crFill); pDC->SelectObject(&brush); pDC->Ellipse(&m_zoomrect); pen.DeleteObject(); brush.DeleteObject(); } ////////////////////////////////////////////////////////////////////// // CTextA Class CTextA::CTextA(short x1, short y1, WORD nSize, COLORREF crTextColor, COLORREF crBkground, short nAngle, UINT nFlags, char* format, va_list argptr) : CShape(x1, y1, crTextColor) { // Die Member-Variablen der Klasse initialisieren. m_nSize = nSize; m_crBkground= crBkground; m_nBkMode = OPAQUE; m_nAngle = nAngle; m_nFlags = nFlags; // Da die Befehle TextOut und DrawText (in CTextBox benutzt) // teilweise verschiedene numerische Konstanten fuer die Ausrichtung benutzen, // jedoch global die einundselben verwendet werden sollen, muessen die flags, // die sich unterscheiden veraendert werden. __changeflag(m_nFlags, DT_VCENTER, TA_BASELINE); __changeflag(m_nFlags, DT_CENTER, TA_CENTER); m_string = (char*) malloc(_MAX_STRING); // Einen ausreichend grossen Speicherblock zuweisen. m_nCount = vsprintf(m_string, format, argptr); // Aus der Argumentenliste einen string generieren. m_string = (char*) realloc(m_string, m_nCount+1); // Den Speicherblock auf die benoetigte Groesse verkleinern. } void CTextA::Draw(CDC* pDC) { // Setzen einer Schriftart mit speziellen Eignenschaften. CFont font; LOGFONT logfont = {m_nSize, 0, m_nAngle, 0, FW_DONTCARE, 0, 0, 0, DEFAULT_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH, "Arial"}; font.CreatePointFontIndirect(&logfont, pDC); pDC->SelectObject(&font); pDC->SetTextColor(m_crColor); // Textfarbe setzen. if (m_nBkMode == OPAQUE) // Wenn undurchsichtig, ... pDC->SetBkColor(m_crBkground); // ...dann Hintergrundfarbe setzen. pDC->SetBkMode(m_nBkMode); // Festlegen ob durchsichtig oder undurchsichtig. pDC->SetTextAlign(m_nFlags); // Setzen der Textausrichtung. pDC->TextOut(m_x, m_y, m_string, m_nCount); // Ausgabe des Textes. font.DeleteObject(); // Loeschen der Ausgewaehlten Schriftcharakteristik } ////////////////////////////////////////////////////////////////////// // CTextBox Class CTextBox::CTextBox(RECT rect, WORD nSize, COLORREF crText, COLORREF crFrame, COLORREF crFill, UINT nFormat, char* format, va_list argptr) : CShape(NULL, NULL, crText) { m_rect = rect; m_nSize = nSize; m_nFormat = nFormat; m_crFrame = crFrame; m_crFill = crFill; m_string = (char*) malloc(_MAX_STRING); // Einen ausreichend grossen Speicherblock zuweisen. m_nCount = vsprintf(m_string, format, argptr); // Aus der Argumentenliste einen string generieren. m_string = (char*) realloc(m_string, m_nCount+1); // Den Speicherblock auf die benoetigte Groesse verkleinern. } void CTextBox::Draw(CDC* pDC) { // Setzen einer Schriftart mit speziellen Eignenschaften. CFont font; font.CreatePointFont(m_nSize, "Arial", pDC); pDC->SelectObject(&font); pDC->SetTextColor(m_crColor); // Textfarbe setzen. pDC->SetBkMode(TRANSPARENT); // Festlegen auf durchsichtig. // Zeichnen eines fuellenden Rechteckes. if (m_crFrame != (COLORREF)-1) { CRectangle rectangle(m_rect, m_crFrame, m_crFill); rectangle.Draw(pDC); } m_rect.DeflateRect(1, 1, 1, 1); // Verkleinern des virtuellen Rechteckes // um die Linienbreite des Rahmens. pDC->SetTextAlign(NULL); // Textausrichtung zuruecksetzen. pDC->DrawText(m_string, m_nCount, &m_rect, m_nFormat); // Text ausgeben. font.DeleteObject(); }