青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品

l

成都手游碼農一枚
隨筆 - 32, 文章 - 0, 評論 - 117, 引用 - 0
數據加載中……

[cocos2d-x] RichText 雜記二。

廢話不多說,先上成果圖。




目前完成了基本的簡析功能,還差圖片,表情以及動畫的部分,以及后期優化工作,最最后的代碼整理。- -。

接下來就分享下整個實現:
1.繪制采用freetype庫實現,支持加粗,斜體,漸變(這個自己算下就可以了)以及描邊,其中描邊估計是最麻煩的,其它都很簡單,網上也有很多實現方式,這里我就主要說說描邊了,
  描邊方式也很多,但是大多效果都不太好,所以最后還是決定用freetype api來實現而不用自己去處理,整個實現可以參考:http://blog.sina.com.cn/s/blog_69a2aeff0100ol7e.html

  1 bool Font::border(Word& word, unsigned int color1, unsigned int color2, unsigned int border)
  2 {
  3     if (!ok())
  4     {
  5         return false;
  6     }
  7 
  8     FT_Face face  = m_size->face;
  9 
 10     FT_UInt index = FT_Get_Char_Index(face, FT_ULong(word.m_code));
 11     if (!index)
 12     {
 13         return false;
 14     }
 15 
 16     if (FT_Load_Glyph(face, index, FT_LOAD_NO_BITMAP))
 17     {
 18         return false;
 19     }
 20 
 21     FT_Glyph glyph;
 22     if (FT_Get_Glyph(face->glyph, &glyph))
 23     {
 24         return false;
 25     }
 26 
 27     FT_Stroker stroker;
 28     if (FT_Stroker_New(s_library, &stroker))
 29     {
 30         return false;
 31     }
 32 
 33     FT_Stroker_Set(stroker, (int)(border * 64), FT_STROKER_LINECAP_ROUND,  FT_STROKER_LINEJOIN_ROUND, 0);
 34 
 35     if (FT_Glyph_StrokeBorder(&glyph, stroker, 0, 1))
 36     {
 37         return false;
 38     }
 39 
 40     FT_Outline *outline = &reinterpret_cast<FT_OutlineGlyph>(glyph)->outline;
 41 
 42     FT_BBox bbox;
 43     FT_Glyph_Get_CBox(glyph, FT_GLYPH_BBOX_GRIDFIT, &bbox);
 44 
 45     int width = (bbox.xMax - bbox.xMin) >> 6;
 46     int rows  = (bbox.yMax - bbox.yMin) >> 6;
 47 
 48     FT_Bitmap *bitmap = &face->glyph->bitmap; 
 49 
 50     word.m_width    = width;
 51     word.m_height   = rows;
 52     word.m_drawX    = face->glyph->metrics.horiBearingX >> 6;
 53     word.m_drawY    = face->glyph->metrics.horiBearingY >> 6;
 54     word.m_advanceX = face->glyph->metrics.horiAdvance  >> 6;
 55     word.m_buffer = new unsigned char[word.m_width * word.m_height * 4];
 56     memset(word.m_buffer, 0, word.m_width * word.m_height * 4);
 57 
 58     unsigned char* buffer = word.m_buffer;
 59         
 60     FT_Raster_Params params;
 61     FT_Bitmap bmp;
 62 
 63     bmp.buffer = new unsigned char[width * rows];
 64     memset(bmp.buffer, 0, width * rows);
 65     bmp.width       = width;
 66     bmp.rows        = rows;
 67     bmp.pitch       = width;
 68     bmp.pixel_mode  = FT_PIXEL_MODE_GRAY;
 69     bmp.num_grays   = 256;
 70 
 71     memset(&params, 0, sizeof (params));
 72     params.source   = outline;
 73     params.target   = &bmp;
 74     params.flags    = FT_RASTER_FLAG_AA;
 75     FT_Outline_Translate(outline,-bbox.xMin,-bbox.yMin);
 76     FT_Outline_Render(s_library, outline, &params);
 77     unsigned char* buffer1 = bmp.buffer;
 78         
 79     FT_BBox bbox_in;
 80     FT_Glyph glyph_fg;
 81     FT_Get_Glyph(face->glyph, &glyph_fg);
 82     FT_Glyph_Get_CBox(glyph_fg, FT_GLYPH_BBOX_GRIDFIT,&bbox_in);
 83 
 84     bmp.buffer = new unsigned char[width * rows];
 85     memset(bmp.buffer, 0, width * rows);
 86     bmp.width       = width;
 87     bmp.rows        = rows;
 88     bmp.pitch       = width;
 89     bmp.pixel_mode  = FT_PIXEL_MODE_GRAY;
 90     bmp.num_grays   = 256;
 91     outline = &reinterpret_cast<FT_OutlineGlyph>(glyph_fg)->outline;
 92     memset(&params, 0, sizeof (params));
 93     params.source   = outline;
 94     params.target   = &bmp;
 95     params.flags = FT_RASTER_FLAG_AA;
 96     FT_Outline_Translate(outline,-bbox.xMin,-bbox.yMin);
 97     FT_Outline_Render(s_library, outline, &params);
 98     unsigned char* buffer2 = bmp.buffer;
 99 
100     int pitch = width;
101     for (int yy = 0; yy < rows; ++yy)
102     {
103         for (int xx = 0; xx < width; ++xx)
104         {
105             int si = yy * word.m_width * 4 + xx * 4;
106             int alpha1 = buffer1[yy * pitch + xx];
107 
108             unsigned char sr = (color1 & 0xFF0000) >> 16,
109                           sg = (color1 & 0xFF00  ) >> 8,
110                           sb = (color1 & 0xFF    );
111 
112             unsigned char dr = (color2 & 0xFF0000) >> 16,
113                           dg = (color2 & 0xFF00  ) >> 8,
114                           db = (color2 & 0xFF    );
115 
116             if (alpha1)
117             {
118                 buffer[si + 0] = dr;
119                 buffer[si + 1] = dg;
120                 buffer[si + 2] = db;
121                 buffer[si + 3] =  alpha1;
122             }
123 
124             int alpha2 = buffer2[yy * pitch + xx];
125             if (alpha2)
126             {
127                 buffer[si + 0] = dr + ( sr - dr) * alpha2 / 255.0f;
128                 buffer[si + 1] = dg + ( sg - dg) * alpha2 / 255.0f;
129                 buffer[si + 2] = db + ( sb - db) * alpha2 / 255.0f;
130                 buffer[si + 3] =  min(255, alpha1 + alpha2);
131             }
132         }
133     }
134 
135     delete [] buffer1;
136     delete [] buffer2;
137 
138     FT_Stroker_Done(stroker);
139 
140     return true;
141 }

2.字體緩存,緩存可以參考 FTC_Manager 緩存子系統,可以參看 ft_cache.h 的說明。

3.布局,目前我的布局方案:
IElement 接口:用于獲取每個元素的大小,以及保存元素的位置信息,后面可以用于處理 Hittest。
ElementCollection :具體說來就是一行,由多個 Element 組成,繪制前線設置x,y值,然后調用本身layout函數來布局,最后父節點可以獲取高度和寬度用于計算。
RowCollection :由多個ElementCollection構成,主要用于緩存所有結點信息,提供layout接口后計算出整個布局的包圍盒,然后生成紋理在繪制。
RichDoc : 內部有一個 RowCollection,主要用于將字符串轉換成IElement,并處理換行等。
TextElement :文本元素,如果是漢字就一個字對應一個TextElement,單詞則由多個構成,這樣方便布局。
后期可能還有 ImageElement 等等。

補充:ElementCollection 中元素,即通常的一行,如果未滿行而剩余空間又小于一個固定值,我這里大概設置的30,那么就應該吧這30的空隙填充到每個元素之間,這樣布局出來的效果行尾基本都是對齊的,如果空隙太大就不應該插入。

4.字符串簡析
這個看自己的愛好,可以自由發揮,這里貼出效果圖的布局文本。

#{effect="border" color1="ffffff"}#{effect="border" color1="ff0000"}英文原文:Developer Hacks His Microwave Into The Microwave Of The Future#{}

普通的#{effect="italic" color1="ff00ff" value="25"}家用微波爐#{}可以說是非常不智能的產品,買回來不僅時間需要人工設定,使用過程中,我們也很少會根據事物的不同,選擇對應的設置,只要能熱食物就行。

所以,當我看到開發者 Nathan Broadbent 跟他的微波爐說話,語音控制微波爐,并且能夠自動設置時間,甚至,你只需要掃描一下產品的條形碼,微波爐便能自動識別對應的模式以及分鐘數時,我感覺我快要窒息了。

這款微波爐被命名為 #{effect="border" color1="00ff00"}"Raspberry Picrowave"#{},顧名思義,是一臺同樹莓派相連的微波爐設備。

經過調試之后,這款微波爐具備以下功能:

        #{effect="gradient" color1="220022" color2="ff0000"}通過網絡,自動調節時間。#{}
        #{effect="gradient" color1="220022" color2="ff0000"}通過將對應食物的數據錄入自建的在線數據庫,只需掃描條形碼,微波爐便會自動開始運作。#{}
        #{effect="gradient" color1="220022" color2="ff0000"}可自定義聲效。#{}
    你可以使用手機或者 #{effect="bold" color1="00ffff"}iPad#{} 來控制微波爐。適用場景包括:你可以提前放置食物,然后通過手機等設備來操控微波爐,或者你也可以用這項功能嚇嚇你的小伙伴。
當食物熱好之后,它還能發推!
讓微波爐更加智能化,本該是大型的微波爐廠商自己該做的事情,但市面上一直沒有智能和人性化的微波爐出現,直到今天,我們人需要人工設置時間. 好的是,相信這款 Raspberry Picrowave 的出現,可能會推動微波爐智能化的進程,將物聯網的生活往前又推進了一步,不過這款微波爐只是極客們自己的玩具,并沒有量產,普及到普通消費者的家中還需要一段時間。#{}

PS:附帶一張真機測試圖,沒想象中感覺好。
PS:造成失真是猶豫界面被拉伸導致,所以如果不拉升,效果還是一樣的。

posted on 2013-07-14 16:57 l1989 閱讀(9198) 評論(19)  編輯 收藏 引用 所屬分類: C++ 、游戲

評論

# re: [cocos2d-x] RichText 雜記二。  回復  更多評論   

不錯。希望能看到成品。
2013-07-14 19:51 | 小笨象

# re: [cocos2d-x] RichText 雜記二。  回復  更多評論   

挺不錯, 謝謝博主分享
2013-07-14 23:30 | weibo

# re: [cocos2d-x] RichText 雜記二。  回復  更多評論   

東西很好,可是具體調用該怎么用?我調用了沒顯示。Word那個struct 應該怎么填充,怎么顯示在cocos2d-x的層上。厚顏討教。
2013-07-15 21:10 | alsky

# re: [cocos2d-x] RichText 雜記二。  回復  更多評論   

@alsky
class Word
{
public:
Word(unsigned long code);
~Word();

unsigned long m_code; // 字符 unicode 編碼
int m_height; // 字符高度
int m_width; // 字符寬度
int m_drawX; // 字符繪制的水平偏移
int m_drawY; // 字符繪制基線上方偏移
int m_advanceX; // 字符步進
unsigned char* m_buffer; // 字符像素信息緩存
};

轉換為 CCSprite
CCTexture2D* texture = new CCTexture2D();
if (!texture->initWithData(m_paBuffer, kCCTexture2DPixelFormat_RGBA8888,
m_nWidth, m_nHeight, CCSizeMake(m_nWidth, m_nHeight)))
{
return NULL;
}
return CCSprite::createWithTexture(texture);
2013-07-15 21:38 | AZL

# re: [cocos2d-x] RichText 雜記二。  回復  更多評論   

@AZL
感謝指導?。?br>關于 texture->initWithData(m_paBuffer, kCCText
m_paBuffer是什么?
是不是 運行了
border(*wordp,0xcccccc,0xdd2211,2);函數以后的
wordp->m_buffer ?

我這樣做了以后,出來了一個白色圖塊,對顏色什么修改都沒反應。
我理解的border這個函數,你最后要用的是 wordp-》m_buffer
不知道理解錯了沒有。
2013-07-15 23:43 | alsky

# re: [cocos2d-x] RichText 雜記二。  回復  更多評論   

@alsky
差不多吧,你可以把多個word的像素緩存考到一個大的位圖結構(RGBA),然后直接initWithData初始紋理。
2013-07-16 09:02 | AZL

# re: [cocos2d-x] RichText 雜記二。  回復  更多評論   

@AZL
謝謝,
當我加了句
FT_Set_Char_Size(face,48<<6,48<<6, 76 , 76);
以后成功了,
但是這個很怪異,這個76換成別的都不行,我也不知道為什么一定要是76,
這個應該是分辨率的,但是我不知道這個應該從哪里取。
不知道你那時是怎樣解決的,請一定指教啊
2013-07-16 16:07 | alsky

# re: [cocos2d-x] RichText 雜記二。  回復  更多評論   

調用:
Word *wordp = new Word(L'中');
says->border(*wordp,0xcccccc,0x12cccc,2);

函數:
bool Says::border(Word& word, unsigned int color1, unsigned int color2, unsigned int border)
{

FT_Library m_library;

FT_Face face;// = m_size->face;

//打開字庫文件,創建一個字體
FT_Init_FreeType(&m_library);
FT_New_Face(m_library,"C:\\WINDOWS\\Fonts\\msyh.ttf",0,&face);


FT_UInt index = FT_Get_Char_Index(face,word.m_code);
if (!index)
{
return false;
}

FT_Set_Char_Size(face,48<<6,48<<6,76,76);
。。。
}后面完全一樣省略

我現在的效果是 改變分辨率,76,76那里可以看到‘中’字,如果要看到‘國’字,又要把分辨率調成75,75,要看到英文字母又要改變。。。
我都要抓狂了。應該不是改分辨率那里啊。。。
2013-07-16 21:53 | alsky

# re: [cocos2d-x] RichText 雜記二。  回復  更多評論   

@alsky
還有,word里面的m_code
我用的wchar ,沒有用//unsigned long
2013-07-16 21:55 | alsky

# re: [cocos2d-x] RichText 雜記二。  回復  更多評論   

!我找到原因了,是我
initWithData(wordp->m_buffer, kCCTexture2DPixelFormat_RGBA8888,
m_nWidth, m_nHeight, CCSizeMake(m_nWidth, m_nHeight)))
時,m_nWidth,和高指定死了,應該去讀自高就對了,真是毫無技術含量的問題,浪費大大時間了。

謝謝大大了。

最后,我想看大大寫個 freetype 逐字顯示的 教程。。。
2013-07-16 22:09 | alsky

# re: [cocos2d-x] RichText 雜記二。  回復  更多評論   

很不錯的 謝謝分享
2013-07-17 16:45 | tb

# re: [cocos2d-x] RichText 雜記二。  回復  更多評論   

如果彩色的文本遇到換行,是自動換行還是手動編輯?
看這里好像是要手動換行
#{effect="gradient" color1="220022" color2="ff0000"}通過將對應食物的數據錄入自建的在線數據庫,只需掃描條形碼,微波爐便會自動開始運作。#{}
#{effect="gradient" color1="220022" color2="ff0000"}可自定義聲效。#{}
2013-08-12 11:33 | abao2000

# re: [cocos2d-x] RichText 雜記二。  回復  更多評論   

你好能給個工程下載的么?
2013-09-09 18:39 | CQC

# re: [cocos2d-x] RichText 雜記二。  回復  更多評論   

很好,支持一下。 希望博主早日完成
2013-10-07 18:01 | hzt

# re: [cocos2d-x] RichText 雜記二。  回復  更多評論   

樓主,能分享一下代碼嗎
2013-12-05 23:53 | Damein

# re: [cocos2d-x] RichText 雜記二。  回復  更多評論   

LZ 我在cocos2d-x 2.x里面加的freetype 渲染的字體 有的對有的不對 這是什么原因
2015-07-06 10:36 | u_tansuo

# re: [cocos2d-x] RichText 雜記二。  回復  更多評論   

@alsky
我的跟你的情況差不多 不同字號 同一句話 渲染出來有的字符就是錯的??

FT_Set_Char_Size(face,48<<6,48<<6,76,76)改變后兩個參數 ,渲染出來的效果也變化,有的字符正常 有的字符錯誤 http://www.cocoachina.com/bbs/read.php?tid-309167.html 這是效果
2015-07-06 10:55 | u_tansuo

# re: [cocos2d-x] RichText 雜記二。[未登錄]  回復  更多評論   

樓主, FT_Stroker_Set(stroker, (int)(border * 64), FT_STROKER_LINECAP_ROUND, FT_STROKER_LINEJOIN_ROUND, 0)中border的初始值是多少?
2015-11-24 11:43 | 天涯

# re: [cocos2d-x] RichText 雜記二。[未登錄]  回復  更多評論   

能說說buffer1與buffer2的區別嗎?謝謝
2015-11-27 10:37 | 天涯
青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品
  • <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            欧美激情国产日韩| 久久在线免费| 国产欧美日韩三区| 欧美一区2区三区4区公司二百| 亚洲在线视频观看| 久久成人精品| 亚洲黄色视屏| 一本大道久久精品懂色aⅴ | 亚洲国产精品高清久久久| 久久九九电影| 一区二区三区成人| 亚洲欧美日本视频在线观看| 国产日韩欧美日韩| 欧美国产一区二区三区激情无套| 欧美激情一区二区三级高清视频| 亚洲欧美日韩国产成人| 久久av在线看| 亚洲午夜久久久久久尤物| 欧美一区二区久久久| 亚洲精品字幕| 欧美一级久久久| 亚洲免费电影在线观看| 亚洲欧美日韩一区二区三区在线观看| 伊人久久噜噜噜躁狠狠躁| 亚洲欧洲日产国产综合网| 国产伦精品一区二区三区| 亚洲二区在线| 国产午夜精品麻豆| 亚洲精品一区二区三| 狠色狠色综合久久| 亚洲一区二区三区精品视频| 亚洲第一福利在线观看| 亚洲综合欧美| 亚洲私人影院| 欧美1区2区| 久久久久综合| 国产精品日韩一区二区三区| 亚洲电影av| 在线观看成人网| 欧美制服丝袜第一页| 亚洲欧美日韩中文在线制服| 奶水喷射视频一区| 久久久久久亚洲精品不卡4k岛国| 欧美日韩一区二| 欧美激情一区二区三区四区 | 久久国产精品电影| 亚洲一区二区三区四区中文| 欧美成人精品在线观看| 麻豆91精品| 国产婷婷成人久久av免费高清| 日韩亚洲欧美一区| 中日韩午夜理伦电影免费| 另类天堂av| 欧美激情精品久久久久久大尺度 | 国产一区二区成人久久免费影院| 99视频国产精品免费观看| 亚洲国语精品自产拍在线观看| 欧美一激情一区二区三区| 欧美一区二区三区四区视频| 欧美日韩一区二区三区在线视频 | 91久久精品日日躁夜夜躁欧美| 狠狠色综合日日| 久久精品欧美日韩精品| 久久尤物电影视频在线观看| 国内久久婷婷综合| 亚洲一区免费| 美女久久网站| 国产精品久久久久久久久借妻 | 亚洲欧美在线高清| 午夜激情亚洲| 国产一区免费视频| 久久久99国产精品免费| 欧美α欧美αv大片| 亚洲狠狠丁香婷婷综合久久久| 欧美xxx在线观看| 亚洲毛片播放| 欧美夜福利tv在线| 国内精品久久久久伊人av| 久久久久国内| 亚洲福利一区| 亚洲午夜久久久久久久久电影网| 国产精品久久一卡二卡| 欧美在线啊v一区| 亚洲第一色在线| 亚洲午夜久久久久久久久电影网| 国产精品亚发布| 久久午夜电影网| 亚洲六月丁香色婷婷综合久久| 亚洲午夜av| 狠狠干成人综合网| 欧美精品电影在线| 亚洲综合色婷婷| 亚洲大胆人体视频| 亚洲在线视频| 在线精品视频在线观看高清| 欧美精品一区二区三| 欧美一级电影久久| 亚洲精品一区二区三| 久久久久久久综合| 日韩午夜在线电影| 国产日韩综合| 欧美巨乳在线| 久久精品成人欧美大片古装| 日韩一级精品| 亚洲成人在线视频播放 | 亚洲精品国久久99热| 先锋影音网一区二区| 91久久精品美女| 国产女同一区二区| 欧美精品一区在线观看| 久久精品二区亚洲w码| 一本色道久久综合亚洲精品不| 久久亚洲影院| 欧美一区二区三区免费观看视频| 最新亚洲视频| 黄色在线成人| 国产一区成人| 国产精品影片在线观看| 欧美美女bbbb| 欧美激情国产日韩| 麻豆成人在线| 久久免费视频在线观看| 午夜精彩视频在线观看不卡| 亚洲精品一区二区三区av| 欧美福利在线观看| 久久一区二区三区四区| 亚洲激情一区二区| 亚洲国产欧美在线人成| 国产美女精品免费电影| 欧美日韩在线免费观看| 蜜臀久久久99精品久久久久久| 午夜精品国产更新| 亚洲一区二区在线免费观看| 一个色综合av| 9国产精品视频| 日韩视频免费看| 亚洲欧洲一区二区三区| 欧美高清在线观看| 欧美jjzz| 欧美激情视频在线播放| 亚洲成人资源| 亚洲日本无吗高清不卡| 亚洲黄色性网站| 亚洲精品永久免费| 99精品欧美一区二区三区| 日韩视频免费观看| 中日韩视频在线观看| 亚洲性视频h| 性亚洲最疯狂xxxx高清| 欧美一区二区三区四区在线观看地址| 亚洲欧美国产va在线影院| 欧美一级视频| 玖玖视频精品| 欧美日韩你懂的| 国产精品亚洲一区| 韩国欧美一区| 99视频热这里只有精品免费| 一本色道久久加勒比88综合| 亚洲欧美日韩国产中文在线| 午夜日韩av| 鲁大师成人一区二区三区| 欧美激情一区二区三级高清视频| 亚洲人成小说网站色在线| 在线一区二区三区四区五区| 亚洲在线视频免费观看| 久久精品男女| 欧美日韩免费观看一区二区三区 | 午夜日韩视频| 欧美成人午夜激情视频| 日韩亚洲一区二区| 久久国产精品久久久久久久久久 | 一本大道av伊人久久综合| 亚洲欧美三级伦理| 欧美黄色片免费观看| 亚洲乱码视频| 久久国产综合精品| 欧美视频日韩视频| 伊人夜夜躁av伊人久久| 亚洲一区二区精品| 欧美成年网站| 亚洲欧美日韩在线高清直播| 猛干欧美女孩| 国产日韩一级二级三级| 一本一本久久a久久精品牛牛影视| 欧美伊人影院| 亚洲精品裸体| 久久久久在线| 国产精品手机视频| 一区二区欧美日韩| 美国十次了思思久久精品导航| 一区二区三区精品视频| 久久综合伊人77777| 国产欧美日韩视频一区二区三区| 日韩亚洲国产精品| 免费高清在线一区| 羞羞答答国产精品www一本| 欧美日韩免费在线| 日韩一二三区视频| 欧美成人精品在线观看| 欧美一区二区三区视频|