Gwen::Rect Text::GetCharacterPosition( int iChar ) { if ( !m_Lines.empty() ) { TextLines::iterator it = m_Lines.begin(); TextLines::iterator itEnd = m_Lines.end(); int iChars = 0; while ( it != itEnd ) { Text* pLine = *it; ++it; iChars += pLine->Length(); if ( iChars <= iChar ) { continue; } iChars -= pLine->Length(); Gwen::Rect rect = pLine->GetCharacterPosition( iChar - iChars ); rect.x += pLine->X(); rect.y += pLine->Y(); return rect; } } if ( Length() == 0 || iChar == 0 ) { Gwen::Point p = GetSkin()->GetRender()->MeasureText( GetFont(), L" " ); return Gwen::Rect( 1, 0, 0, p.y ); } UnicodeString sub = m_String.GetUnicode().substr( 0, iChar ); Gwen::Point p = GetSkin()->GetRender()->MeasureText( GetFont(), sub ); return Rect( p.x, 0, 0, p.y ); }
Gwen::Rect Text::GetLineBox( int i ) { Text* line = GetLine(i); if(line != NULL) { Gwen::Point p = GetSkin()->GetRender()->MeasureText( GetFont(), line->m_String.GetUnicode()); return Gwen::Rect(line->X(), line->Y(), Clamp(p.x, 1,p.x), Clamp(p.y, 1,p.y) ); } else { Gwen::Point p = GetSkin()->GetRender()->MeasureText( GetFont(), m_String.GetUnicode()); return Gwen::Rect(0, 0, Clamp(p.x, 1,p.x), Clamp(p.y, 1,p.y) ); } }
int Text::GetClosestCharacter( Gwen::Point p ) { if ( !m_Lines.empty() ) { TextLines::iterator it = m_Lines.begin(); TextLines::iterator itEnd = m_Lines.end(); int iChars = 0; while ( it != itEnd ) { Text* pLine = *it; ++it; iChars += pLine->Length(); if ( p.y < pLine->Y() ) continue; if ( p.y > pLine->Bottom() ) continue; iChars -= pLine->Length(); int iLinePos = pLine->GetClosestCharacter( Gwen::Point( p.x - pLine->X(), p.y - pLine->Y() ) ); //if ( iLinePos > 0 && iLinePos == pLine->Length() ) iLinePos--; iLinePos--; return iChars + iLinePos; } } int iDistance = 4096; int iChar = 0; for ( size_t i=0; i<m_String.GetUnicode().length()+1; i++ ) { Gwen::Rect cp = GetCharacterPosition( i ); int iDist = abs(cp.x - p.x) + abs(cp.y - p.y); // this isn't proper if ( iDist > iDistance ) continue; iDistance = iDist; iChar = i; } return iChar; }