Cocos2d-x项目移植到WP8系列之八:CCLabelTTF显示中文不换行

 原文链接: http://www.cnblogs.com/zouzf/p/3985330.html

在wp8平台上,CCLabeTTF显示中文不会自动换行,看了下源码,原来底层的实现是根据text的空格进行判断的,每遇到一个空格就判断是否超过label的宽度,超过就换行,但text如果是中文的话,哪来的空格给换行~~

以下实现全部参考 http://blog.csdn.net/hopingwhite/article/details/38414917 ,整理后的代码如下:

在CCFreeTypeFont.h里的CCFreeTypeFont类添加两个方法:

 FT_Error addLine(const std::string& line);
 void endLine_chinese();

实现如下:

  1 void CCFreeTypeFont::endLine_chinese() 
  2 {
  3     if(m_currentLine)
  4     {
  5         m_lines.push_back(m_currentLine);
  6         compute_bbox(m_currentLine->glyphs, &m_currentLine->bbox);
  7         m_currentLine->width = m_currentLine->bbox.xMax - m_currentLine->bbox.xMin;
  8         m_textWidth = max(m_textWidth,m_currentLine->bbox.xMax - m_currentLine->bbox.xMin);
  9         m_textHeight += m_lineHeight;
 10         m_currentLine = NULL;
 11     }
 12 }
 13 
 14 
 15 
 16 FT_Error CCFreeTypeFont::addLine(const std::string& line)
 17 {
 18         wchar_t *       pwszBuffer = nullptr;
 19 
 20         int num_chars = line.size();
 21         int nBufLen = num_chars + 1;
 22         pwszBuffer = new wchar_t[nBufLen];
 23         if (!pwszBuffer)
 24         {
 25                 return -1;
 26         }
 27 
 28         memset(pwszBuffer, 0, nBufLen);
 29         num_chars = MultiByteToWideChar(CP_UTF8, 0, line.c_str(), num_chars, pwszBuffer, nBufLen);
 30         pwszBuffer[num_chars] = '';
 31 
 32         int maxWidth = m_inWidth ? m_inWidth : m_windowWidth;
 33 
 34         newLine();
 35         FT_Vector pen = m_currentLine->pen;
 36         FT_GlyphSlot    slot = m_face->glyph;
 37         FT_UInt                 glyph_index;
 38         FT_UInt                 previous = 0;
 39         FT_Error                error = 0;
 40         unsigned int    numGlyphs = 0;
 41 
 42         FT_Bool useKerning = FT_HAS_KERNING(m_face);
 43 
 44         int n = 0;
 45         while (n < num_chars)
 46         {
 47                 TGlyph glyph;
 48 
 49                 /* convert character code to glyph index */
 50                 FT_ULong c = pwszBuffer[n++];
 51                 glyph_index = FT_Get_Char_Index(m_face, c);
 52 
 53                 if (useKerning && previous && glyph_index)
 54                 {
 55                         FT_Vector  delta;
 56                         FT_Get_Kerning(m_face, previous, glyph_index,
 57                                 FT_KERNING_DEFAULT, &delta);
 58                         pen.x += delta.x >> 6;
 59                 }
 60 
 61                 /* store current pen position */
 62                 glyph.pos = pen;
 63                 glyph.index = glyph_index;
 64 
 65                 /* load glyph image into the slot without rendering */
 66                 error = FT_Load_Glyph(m_face, glyph_index, FT_LOAD_DEFAULT);
 67                 if (error)
 68                         continue;  /* ignore errors, jump to next glyph */
 69 
 70                 /* extract glyph image and store it in our table */
 71                 error = FT_Get_Glyph(m_face->glyph, &glyph.image);
 72                 if (error)
 73                         continue;  /* ignore errors, jump to next glyph */
 74 
 75                 /* translate the glyph image now */
 76                 FT_Glyph_Transform(glyph.image, 0, &glyph.pos);
 77 
 78                 /* increment pen position */
 79                 pen.x += slot->advance.x >> 6;
 80 
 81                 if (pen.x > maxWidth)
 82                 {
 83                         m_currentLine->pen = pen;
 84                        
 85                         // endLine();
 86                         endLine_chinese();
 87 
 88                         newLine();
 89                         pen = m_currentLine->pen;
 90                         previous = 0;
 91                         n--;
 92                 }
 93                 else
 94                 {
 95                         m_currentLine->glyphs.push_back(glyph);
 96                         /* record current glyph index */
 97                         previous = glyph_index;
 98                 }
 99         }
100 
101         if (m_currentLine)
102         {
103                 m_currentLine->pen = pen;
104                 
105                 //endLine();
106                 endLine_chinese();
107         }
108 
109         CC_SAFE_DELETE_ARRAY(pwszBuffer);
110         return error;
111 }

FT_Error CCFreeTypeFont::initGlyphs(const char* text)的实现改成如下:

 1 FT_Error CCFreeTypeFont::initGlyphs(const char* text) 
 2 {
 3     FT_Error error = 0;
 4     std::stringstream stringStream(text);
 5     std::string line;
 6     vector<std::string> lines;
 7     vector<std::string> words;
 8 
 9     m_textWidth = 0;
10     m_textHeight = 0;
11     // the height of a line of text based on the max height of a glyph in the font size
12     m_lineHeight = ((m_face->size->metrics.ascender) >> 6) - ((m_face->size->metrics.descender) >> 6);
13 
14     m_lines.clear();
15 
16     while(std::getline(stringStream, line) && !error) 
17     {
18       /*  newLine();
19 
20         std::size_t prev = 0, pos;
21         while ((pos = line.find_first_of(" ", prev)) != std::string::npos)
22         {
23             if (pos > prev)
24             {
25                 addWord(line.substr(prev, pos-prev));
26             }
27             prev = pos + 1;
28         }
29         if (prev < line.length())
30         {
31             addWord(line.substr(prev, std::string::npos));
32         }
33         endLine();
34         */
35         addLine(line);
36     }
37 
38     return error;
39 }


再次感谢: http://blog.csdn.net/hopingwhite/article/details/38414917

原文链接: http://www.cnblogs.com/zouzf/p/3985330.html

原文地址:https://www.cnblogs.com/zouzf/p/3985330.html