- AGG的內部格式是 color buf[y][x][v]
CImg的內部格式是 color buf[v][y][x]
其中color爲單通道顏色值、v代表顏色通道(如RGB三色)、x,y是座標。我們這裏讓CImg的z軸爲1,即二維圖像。 - 我們得找個方法可以方便地互相轉換,這裏我們選用multi_array來做這件事(另,GIL也是一個不錯的候選方案,見本站GIL教程 )。
- #include "boost/multi_array.hpp" // multi_array
- #include "cimg.h" // CImg
- #include <agg_pixfmt_rgb.h> //後面全是AGG的
- #include <agg_scanline_u.h>
- #include <agg_renderer_scanline.h>
- #include <../font_win32_tt/agg_font_win32_tt.h>
- #include <agg_font_cache_manager.h>
- #include <agg_conv_bspline.h>
- #include <agg_path_storage.h>
- #include <agg_conv_curve.h>
- #include <agg_conv_transform.h>
- #include <agg_ellipse.h>
- #include <agg_trans_single_path.h>
- using cimg_library::CImg;
- int main () {
- // AGG畫圖,寫了一行字
- char buf[200][300][3];
- agg::rendering_buffer rbuf(
- (unsigned char *)buf,
- 300, 200,
- 300*3);
- agg::pixfmt_rgb24 pixf(rbuf);
- agg::renderer_base<agg::pixfmt_rgb24> renb(pixf);
- typedef agg::font_engine_win32_tt_int16 fe_type;
- typedef agg::font_cache_manager<fe_type> fcman_type;
- renb.clear(agg::rgba(0.5,0.5,1));
- fe_type font(::GetDC(0));
- fcman_type font_manager(font);
- font.height(32.0);
- font.flip_y(true );
- font.hinting(true );
- if (!font.create_font( "Comic Sans MS" ,agg::glyph_ren_outline)) return -1;
- //座標轉換管道
- typedef agg::conv_curve<
- fcman_type::path_adaptor_type
- > cc_pa_type;
- cc_pa_type ccpath(font_manager.path_adaptor());
- typedef agg::conv_transform<cc_pa_type,
- agg::trans_single_path> ct_cc_pa_type;
- agg::trans_single_path trans_path;
- ct_cc_pa_type ctpath(ccpath, trans_path);
- agg::path_storage ps;
- ps.move_to(20,100);
- ps.line_rel(80,50);
- ps.line_rel(100,-100);
- ps.line_rel(100,100);
- agg::conv_bspline<agg::path_storage> cb_ps(ps);
- trans_path.add_path(cb_ps);
- agg::rasterizer_scanline_aa<> ras;
- agg::scanline_u8 sl;
- double x=0, y=0;
- for ( const wchar_t *p = L "http://www.cppprog.com" ; *p; p++)
- {
- const agg::glyph_cache* gc = font_manager.glyph(*p);
- if (gc)
- {
- font_manager.init_embedded_adaptors(gc, x, y);
- ras.add_path(ctpath);
- x += gc->advance_x;
- y += gc->advance_y;
- }
- }
- agg::render_scanlines_aa_solid(ras,sl,renb,agg::rgba(1,0,0));
- // 定義CImg
- CImg<unsigned char > img(300,200,1,3);
- // 用multi_array把AGG圖像數據轉成CImg
- typedef boost::multi_array_ref<unsigned char ,3> array_type;
- // AGG->多維數組
- /**
- * AGG排列是[y][x][v], CImg是[v][y][x]
- * 設y=2, x=1, v=0(C語言默認順序)
- * 則AGG的[2][1][0]對應CImg就是[0][2][1]
- */
- typedef boost::general_storage_order<3> storage;
- array_type::size_type ordering[] = {0,2,1};
- bool ascending[] = { true , true , true };
- array_type array_agg((unsigned char *)buf,boost::extents[3][200][300],storage(ordering,ascending));
- // 把AGG圖像數據賦值給CImg,multi_array_ref內部做轉換工作
- array_type(img.data, boost::extents[3][200][300]) = array_agg;
- // CImg圖像處理
- img.blur(6).noise(10).erode(4);
- // 把CImg處理過的圖像又傳給AGG
- array_agg = array_type(img.data, boost::extents[3][200][300]);
- // AGG在此基礎上畫圖
- agg::render_scanlines_aa_solid(ras,sl,renb,agg::rgba(1,1,0));
- // 給CImg顯示
- array_type(img.data, boost::extents[3][200][300]) = array_agg;
- img.erode(2);
- img.display("view" );
- return 0;
- }
動態多維數組-multi_array
本站有AGG
和CImg
的圖像處理教程,AGG庫傾向於矢量繪圖,CImg傾向於圖像處理。我們可以考慮雙劍合壁,共同來生成我們要的圖像。可是它們的內部數據格式卻不完全相同:
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.