/* sText is UTF-8. If not all of the characters in sText are available in the * font, sAlternateText will be used instead. If there are unavailable characters * in sAlternateText, too, just use sText. */ void BitmapText::SetText( const RString& _sText, const RString& _sAlternateText, int iWrapWidthPixels ) { ASSERT( m_pFont != NULL ); RString sNewText = StringWillUseAlternate(_sText,_sAlternateText) ? _sAlternateText : _sText; if( m_bUppercase ) sNewText.MakeUpper(); if( iWrapWidthPixels == -1 ) // wrap not specified iWrapWidthPixels = m_iWrapWidthPixels; if( m_sText == sNewText && iWrapWidthPixels==m_iWrapWidthPixels ) return; m_sText = sNewText; m_iWrapWidthPixels = iWrapWidthPixels; ClearAttributes(); SetTextInternal(); }
void ColorBitmapText::SetText( const CString& _sText, const CString& _sAlternateText, int iWrapWidthPixels ) { ASSERT( m_pFont ); CString sNewText = StringWillUseAlternate(_sText,_sAlternateText) ? _sAlternateText : _sText; if( iWrapWidthPixels == -1 ) // wrap not specified iWrapWidthPixels = m_iWrapWidthPixels; if( m_sText == sNewText && iWrapWidthPixels==m_iWrapWidthPixels ) return; m_sText = sNewText; m_iWrapWidthPixels = iWrapWidthPixels; //Set up the first color. m_vColors.clear(); ColorChange change; change.c = RageColor ( 1, 1, 1, 1 ); change.l = 0; m_vColors.push_back( change ); m_wTextLines.clear(); CString sCurrentLine = ""; int iLineWidth = 0; CString sCurrentWord = ""; int iWordWidth = 0; int iGlyphsSoFar = 0; for ( unsigned i = 0; i < m_sText.length(); i++ ) { int iCharsLeft = m_sText.length() - i - 1; //First: Check for the special (color) case. CString FirstThree = m_sText.substr( i, 3 ); if ( ( FirstThree.CompareNoCase( "|c0" ) == 0 ) && ( iCharsLeft > 8 ) ) { ColorChange change; int k; sscanf( m_sText.substr( i+3, 2 ).c_str(), "%x", &k ); change.c.r = float( k ) / 255.0f; sscanf( m_sText.substr( i+5, 2 ).c_str(), "%x", &k ); change.c.g = float( k ) / 255.0f; sscanf( m_sText.substr( i+7, 2 ).c_str(), "%x", &k ); change.c.b = float( k ) / 255.0f; change.c.a = 1; change.l = iGlyphsSoFar; if ( iGlyphsSoFar == 0 ) m_vColors[0] = change; else m_vColors.push_back( change ); i+=8; continue; } CString curCStr = m_sText.substr( i, 1 ); char curChar = curCStr.c_str()[0]; int iCharLen = m_pFont->GetLineWidthInSourcePixels( CStringToWstring( curCStr ) ); switch ( curChar ) { case ' ': if ( /*( iLineWidth == 0 ) &&*/ ( iWordWidth == 0 ) ) break; sCurrentLine += sCurrentWord + " "; iLineWidth += iWordWidth + iCharLen; sCurrentWord = ""; iWordWidth = 0; iGlyphsSoFar++; break; case '\n': if ( iLineWidth + iWordWidth > iWrapWidthPixels ) { SimpleAddLine( sCurrentLine, iLineWidth ); if ( iWordWidth > 0 ) iLineWidth = iWordWidth + //Add the width of a space m_pFont->GetLineWidthInSourcePixels( CStringToWstring( " " ) ); sCurrentLine = sCurrentWord + " "; iWordWidth = 0; sCurrentWord = ""; iGlyphsSoFar++; } else { SimpleAddLine( sCurrentLine + sCurrentWord, iLineWidth + iWordWidth ); sCurrentLine = ""; iLineWidth = 0; sCurrentWord = ""; iWordWidth = 0; } break; default: if ( ( iWordWidth + iCharLen > iWrapWidthPixels ) && ( iLineWidth == 0 ) ) { SimpleAddLine( sCurrentWord, iWordWidth ); sCurrentWord = curChar; iWordWidth = iCharLen; } else if ( iWordWidth + iLineWidth + iCharLen > iWrapWidthPixels ) { SimpleAddLine( sCurrentLine, iLineWidth ); sCurrentLine = ""; iLineWidth = 0; sCurrentWord += curChar; iWordWidth += iCharLen; } else { sCurrentWord += curChar; iWordWidth += iCharLen; } iGlyphsSoFar++; break; } } if ( iWordWidth > 0 ) { sCurrentLine += sCurrentWord; iLineWidth += iWordWidth; } if ( iLineWidth > 0 ) SimpleAddLine( sCurrentLine, iLineWidth ); BuildChars(); UpdateBaseZoom(); }
/* sText is UTF-8. If not all of the characters in sText are available in the * font, sAlternateText will be used instead. If there are unavailable characters * in sAlternateText, too, just use sText. */ void BitmapText::SetText( const CString& _sText, const CString& _sAlternateText, int iWrapWidthPixels ) { ASSERT( m_pFont ); CString sNewText = StringWillUseAlternate(_sText,_sAlternateText) ? _sAlternateText : _sText; if( iWrapWidthPixels == -1 ) // wrap not specified iWrapWidthPixels = m_iWrapWidthPixels; if( m_sText == sNewText && iWrapWidthPixels==m_iWrapWidthPixels ) return; m_sText = sNewText; m_iWrapWidthPixels = iWrapWidthPixels; // Break the string into lines. // m_wTextLines.clear(); if( iWrapWidthPixels == -1 ) { split( CStringToWstring(m_sText), L"\n", m_wTextLines, false ); } else { // // Break sText into lines that don't exceed iWrapWidthPixels // (if only one word fits on the line, it may be larger than iWrapWidthPixels). // // TODO: Investigate whether this works in all languages /* It doesn't. I can add Japanese wrapping, at least. We could handle hyphens * and soft hyphens and pretty easily, too. -glenn */ // TODO: Move this wrapping logic into Font CStringArray asLines; split( m_sText, "\n", asLines, false ); for( unsigned line = 0; line < asLines.size(); ++line ) { CStringArray asWords; split( asLines[line], " ", asWords ); CString sCurLine; int iCurLineWidth = 0; for( unsigned i=0; i<asWords.size(); i++ ) { const CString &sWord = asWords[i]; int iWidthWord = m_pFont->GetLineWidthInSourcePixels( CStringToWstring(sWord) ); if( sCurLine.empty() ) { sCurLine = sWord; iCurLineWidth = iWidthWord; continue; } CString sToAdd = " " + sWord; int iWidthToAdd = m_pFont->GetLineWidthInSourcePixels(L" ") + iWidthWord; if( iCurLineWidth + iWidthToAdd <= iWrapWidthPixels ) // will fit on current line { sCurLine += sToAdd; iCurLineWidth += iWidthToAdd; } else { m_wTextLines.push_back( CStringToWstring(sCurLine) ); sCurLine = sWord; iCurLineWidth = iWidthWord; } } m_wTextLines.push_back( CStringToWstring(sCurLine) ); } } BuildChars(); UpdateBaseZoom(); }
/** ColorBitmapText ***********************************************************/ void ColorBitmapText::SetText( const RString& _sText, const RString& _sAlternateText, int iWrapWidthPixels ) { ASSERT( m_pFont ); RString sNewText = StringWillUseAlternate(_sText,_sAlternateText) ? _sAlternateText : _sText; if( iWrapWidthPixels == -1 ) // wrap not specified iWrapWidthPixels = m_iWrapWidthPixels; if( m_sText == sNewText && iWrapWidthPixels==m_iWrapWidthPixels ) return; m_sText = sNewText; m_iWrapWidthPixels = iWrapWidthPixels; // Set up the first color. m_vColors.clear(); ColorChange change; change.c = RageColor (1, 1, 1, 1); change.l = 0; m_vColors.push_back( change ); m_wTextLines.clear(); RString sCurrentLine = ""; int iLineWidth = 0; RString sCurrentWord = ""; int iWordWidth = 0; int iGlyphsSoFar = 0; for( unsigned i = 0; i < m_sText.length(); i++ ) { int iCharsLeft = m_sText.length() - i - 1; // First: Check for the special (color) case. if( m_sText.length() > 8 && i < m_sText.length() - 9 ) { RString FirstThree = m_sText.substr( i, 3 ); if( FirstThree.CompareNoCase("|c0") == 0 && iCharsLeft > 8 ) { ColorChange cChange; unsigned int r, g, b; sscanf( m_sText.substr( i, 9 ).c_str(), "|%*c0%2x%2x%2x", &r, &g, &b ); cChange.c = RageColor( r/255.f, g/255.f, b/255.f, 1.f ); cChange.l = iGlyphsSoFar; if( iGlyphsSoFar == 0 ) m_vColors[0] = cChange; else m_vColors.push_back( cChange ); i+=8; continue; } } char curChar = m_sText[i]; int iCharLen = m_pFont->GetLineWidthInSourcePixels( wstring(1, curChar) ); switch( curChar ) { case ' ': if( /* iLineWidth == 0 &&*/ iWordWidth == 0 ) break; sCurrentLine += sCurrentWord + " "; iLineWidth += iWordWidth + iCharLen; sCurrentWord = ""; iWordWidth = 0; iGlyphsSoFar++; break; case '\n': if( iLineWidth + iWordWidth > iWrapWidthPixels ) { SimpleAddLine( sCurrentLine, iLineWidth ); if( iWordWidth > 0 ) iLineWidth = iWordWidth + //Add the width of a space m_pFont->GetLineWidthInSourcePixels( L" " ); sCurrentLine = sCurrentWord + " "; iWordWidth = 0; sCurrentWord = ""; iGlyphsSoFar++; } else { SimpleAddLine( sCurrentLine + sCurrentWord, iLineWidth + iWordWidth ); sCurrentLine = ""; iLineWidth = 0; sCurrentWord = ""; iWordWidth = 0; } break; default: if( iWordWidth + iCharLen > iWrapWidthPixels && iLineWidth == 0 ) { SimpleAddLine( sCurrentWord, iWordWidth ); sCurrentWord = curChar; iWordWidth = iCharLen; } else if( iWordWidth + iLineWidth + iCharLen > iWrapWidthPixels ) { SimpleAddLine( sCurrentLine, iLineWidth ); sCurrentLine = ""; iLineWidth = 0; sCurrentWord += curChar; iWordWidth += iCharLen; } else { sCurrentWord += curChar; iWordWidth += iCharLen; } iGlyphsSoFar++; break; } } if( iWordWidth > 0 ) { sCurrentLine += sCurrentWord; iLineWidth += iWordWidth; } if( iLineWidth > 0 ) SimpleAddLine( sCurrentLine, iLineWidth ); BuildChars(); UpdateBaseZoom(); }