void CBFontTT::DrawTextDD(BYTE* Text, int X, int Y, int Width, TTextAlign Align, int MaxHeight, int MaxLength) { CBRenderDD* m_Renderer = (CBRenderDD*)Game->m_Renderer; if(FAILED(CreateWinFont())) return; HDC hDC; m_Renderer->m_BackBuffer->GetDC(&hDC); HFONT OldFont = (HFONT)SelectObject(hDC, m_HFont); ::SetBkMode(hDC, TRANSPARENT); int TextX = 0; SetTextAlign(hDC, Align, Width, &TextX); BYTE* ConvertedText = CBTextUtils::ConvertToNative(Game->m_TextEncoding, Text, MaxLength); for(int i=0; i<m_Layers.GetSize(); i++) { ::SetTextColor(hDC, CBUtils::D3D2COLORREF(m_Layers[i]->m_Color)); FormatText(X + TextX+m_Layers[i]->m_OffsetX, Y+m_Layers[i]->m_OffsetY, ConvertedText, hDC, Width, MaxHeight); } ::SelectObject(hDC, OldFont); m_Renderer->m_BackBuffer->ReleaseDC(hDC); DeleteWinFont(); delete [] ConvertedText; }
void InitWinFonts( ) { INT32 FontSlot[WIN_LASTFONT]; memset( WinFonts, 0, sizeof( WinFonts ) ); GetWinFontInfo(); for (int i = 0; i<WIN_LASTFONT; i++) { FontSlot[i] = CreateWinFont(FontInfo[i].LogFont); SetWinFontForeColor(FontSlot[i], &FontInfo[i].Color); } //can't use switch here, because FONT12ARIAL, LARGEFONT1... are variables for (int i=0; i<MAX_WINFONTMAP; i++) { if (i == FONT12ARIAL) {WinFontMap[i] = FontSlot[WIN_12POINTARIAL];} else if (i == LARGEFONT1) {WinFontMap[i] = FontSlot[WIN_LARGEFONT1];} else if (i == SMALLFONT1) {WinFontMap[i] = FontSlot[WIN_SMALLFONT1];} else if (i == TINYFONT1) {WinFontMap[i] = FontSlot[WIN_TINYFONT1];} else if (i == FONT12POINT1) {WinFontMap[i] = FontSlot[WIN_12POINTFONT1];} else if (i == COMPFONT) {WinFontMap[i] = FontSlot[WIN_COMPFONT];} else if (i == SMALLCOMPFONT) {WinFontMap[i] = FontSlot[WIN_SMALLCOMPFONT];} else if (i == FONT10ROMAN) {WinFontMap[i] = FontSlot[WIN_10POINTROMAN];} else if (i == FONT12ROMAN) {WinFontMap[i] = FontSlot[WIN_12POINTROMAN];} else if (i == FONT14SANSERIF) {WinFontMap[i] = FontSlot[WIN_14POINTSANSSERIF];} else if (i == MILITARYFONT1) {WinFontMap[i] = FontSlot[WIN_BLOCKYFONT];} else if (i == FONT10ARIAL) {WinFontMap[i] = FontSlot[WIN_10POINTARIAL];} else if (i == FONT14ARIAL) {WinFontMap[i] = FontSlot[WIN_14POINTARIAL];} else if (i == FONT10ARIALBOLD) {WinFontMap[i] = FontSlot[WIN_10POINTARIALBOLD];} else if (i == BLOCKFONT) {WinFontMap[i] = FontSlot[WIN_BLOCKYFONT];} else if (i == BLOCKFONT2) {WinFontMap[i] = FontSlot[WIN_BLOCKYFONT2];} else if (i == FONT12ARIALFIXEDWIDTH) {WinFontMap[i] = FontSlot[WIN_12POINTARIALFIXEDFONT];} else if (i == FONT16ARIAL) {WinFontMap[i] = FontSlot[WIN_16POINTARIAL];} else if (i == BLOCKFONTNARROW) {WinFontMap[i] = FontSlot[WIN_BLOCKFONTNARROW];} else if (i == FONT14HUMANIST) {WinFontMap[i] = FontSlot[WIN_14POINTHUMANIST];} else {WinFontMap[i] = -1;} } }
int CBFontTT::GetLetterHeight() { if(FAILED(CreateWinFont())) return 0; HDC hDC = CreateCompatibleDC(NULL); SetMapMode(hDC, MM_TEXT); HGDIOBJ OldFont = SelectObject(hDC, m_HFont); SIZE Size; GetTextExtentPoint32(hDC, "Ay", 2, &Size); ::SelectObject(hDC, OldFont); DeleteDC(hDC); DeleteWinFont(); return Size.cy; }
int CBFontTT::GetTextHeight(BYTE* Text, int Width) { if(FAILED(CreateWinFont())) return 0; HDC hDC = CreateCompatibleDC(NULL); SetMapMode(hDC, MM_TEXT); HGDIOBJ OldFont = SelectObject(hDC, m_HFont); BYTE* ConvertedText = CBTextUtils::ConvertToNative(Game->m_TextEncoding, Text); int Ret = FormatText(0, 0, ConvertedText, hDC, Width, -1); delete [] ConvertedText; ::SelectObject(hDC, OldFont); DeleteDC(hDC); DeleteWinFont(); return Ret; }
int CBFontTT::GetTextWidth(BYTE* Text, int MaxLength) { int Ret = 0; if(FAILED(CreateWinFont())) return 0; HDC hDC = CreateCompatibleDC(NULL); SetMapMode(hDC, MM_TEXT); HGDIOBJ OldFont = SelectObject(hDC, m_HFont); BYTE* ConvertedText = CBTextUtils::ConvertToNative(Game->m_TextEncoding, Text); if(Game->m_TextEncoding==TEXT_ANSI) { SIZE Size; int Length = strlen((char*)ConvertedText); GetTextExtentPoint32(hDC, (char*)ConvertedText, Length, &Size); Ret = Size.cx; } else if(Game->m_TextEncoding==TEXT_UTF8) { SIZE Size; int Length = wcslen((wchar_t*)ConvertedText); GetTextExtentPoint32W(hDC, (wchar_t*)ConvertedText, Length, &Size); Ret = Size.cx; } delete [] ConvertedText; ::SelectObject(hDC, OldFont); DeleteDC(hDC); DeleteWinFont(); return Ret; }
void CBFontTT::DrawTextD3D(BYTE* Text, int X, int Y, int Width, TTextAlign Align, int MaxHeight, int MaxLength) { CBRenderD3D* m_Renderer = (CBRenderD3D*)Game->m_Renderer; // find cached surface, if exists int MinPriority = INT_MAX; int MaxPriority = 0; int MinIndex = -1; CBSurface* Surface = NULL; for(int i=0; i<NUM_CACHED_TEXTS; i++) { if(m_CachedTexts[i]==NULL) { MinPriority = 0; MinIndex = i; } else { MaxPriority = max(MaxPriority, m_CachedTexts[i]->m_Priority); if(strcmp(m_CachedTexts[i]->m_Text, (char*)Text)==0 && m_CachedTexts[i]->m_Align==Align && m_CachedTexts[i]->m_Width==Width && m_CachedTexts[i]->m_MaxHeight==MaxHeight && m_CachedTexts[i]->m_MaxLength==MaxLength) { Surface = m_CachedTexts[i]->m_Surface; m_CachedTexts[i]->m_Priority++; break; } else { if(m_CachedTexts[i]->m_Priority < MinPriority) { MinPriority = m_CachedTexts[i]->m_Priority; MinIndex = i; } } } } // not found, create one if(!Surface) { if(FAILED(CreateWinFont())) return; HDC hDC = ::CreateCompatibleDC(NULL); ::SetMapMode(hDC, MM_TEXT); HFONT OldFont = (HFONT)::SelectObject(hDC, m_HFont); ::SetTextColor(hDC, RGB(255,255,255)); ::SetBkColor(hDC, 0x00000000); int TextX = 0; SetTextAlign(hDC, Align, Width, &TextX); BYTE* ConvertedText = CBTextUtils::ConvertToNative(Game->m_TextEncoding, Text, MaxLength); //ExtTextOut(hDC, 0, 0, ETO_OPAQUE, NULL, (char*)Text, strlen((char*)Text), NULL); int Height = FormatText(TextX, 0, ConvertedText, hDC, Width, MaxHeight); Height = max(Height, 1); DWORD* BitmapBits; BITMAPINFO bmi; memset(&bmi, 0, sizeof(BITMAPINFO)); bmi.bmiHeader.biSize = sizeof(BITMAPINFOHEADER); bmi.bmiHeader.biWidth = (int)Width; bmi.bmiHeader.biHeight = -(int)Height; bmi.bmiHeader.biPlanes = 1; bmi.bmiHeader.biCompression = BI_RGB; bmi.bmiHeader.biBitCount = 32; HBITMAP hbmBitmap = ::CreateDIBSection(hDC, &bmi, DIB_RGB_COLORS, (VOID**)&BitmapBits, NULL, 0); HBITMAP OldBitmap = (HBITMAP)::SelectObject(hDC, hbmBitmap); FormatText(TextX, 0, ConvertedText, hDC, Width, MaxHeight); CBImage* Image = new CBImage(Game); Image->CreateFromRaw(BitmapBits, Width, Height); Surface = Image->CreateSurface(); delete Image; ::SelectObject(hDC, OldBitmap); ::SelectObject(hDC, OldFont); ::DeleteObject(hbmBitmap); ::DeleteDC(hDC); DeleteWinFont(); delete [] ConvertedText; // write surface to cache if(m_CachedTexts[MinIndex]!=NULL) delete m_CachedTexts[MinIndex]; m_CachedTexts[MinIndex] = new CBCachedTTFontText; m_CachedTexts[MinIndex]->m_Surface = Surface; m_CachedTexts[MinIndex]->m_Align = Align; m_CachedTexts[MinIndex]->m_Width = Width; m_CachedTexts[MinIndex]->m_MaxHeight = MaxHeight; m_CachedTexts[MinIndex]->m_MaxLength = MaxLength; m_CachedTexts[MinIndex]->m_Priority = MaxPriority + 1; CBUtils::SetString(&m_CachedTexts[MinIndex]->m_Text, (char*)Text); } // and paint it if(Surface) { RECT rc; SetRect(&rc, 0, 0, Surface->GetWidth(), Surface->GetHeight()); for(int i=0; i<m_Layers.GetSize(); i++) { DWORD Color = m_Layers[i]->m_Color; DWORD OrigForceAlpha = m_Renderer->m_ForceAlphaColor; if(m_Renderer->m_ForceAlphaColor!=0) { Color = DRGBA(D3DCOLGetR(Color), D3DCOLGetG(Color), D3DCOLGetB(Color), D3DCOLGetA(m_Renderer->m_ForceAlphaColor)); m_Renderer->m_ForceAlphaColor = 0; } Surface->DisplayTrans(X+m_Layers[i]->m_OffsetX, Y+m_Layers[i]->m_OffsetY, rc, Color); m_Renderer->m_ForceAlphaColor = OrigForceAlpha; } } }