29 #include <wx/strconv.h>
42 #if !defined ( WIN32 ) || defined ( __GNUC__ )
47 int access(
char *filename,
int flag )
50 infile = fopen( filename,
"r" );
61 #define makeunixslash( b ) do { char *I; for ( I = b; *I != 0; *I++ ) if ( *I == '\\' ) *I = '/';} while ( 0 )
69 wxPLDevAGG::wxPLDevAGG() :
72 mPixFormat( mRenderingBuffer ),
73 mRendererBase( mPixFormat ),
74 mRendererSolid( mRendererBase ),
79 mConvStroke( mConvCurve ),
80 mPathTransform( mConvCurve, mTransform ),
81 mStrokeTransform( mConvStroke, mTransform ),
84 mFontManager( mFontEngine ),
85 mCurves( mFontManager.path_adaptor() ),
90 mStrokeOpacity( 255 ),
91 mColorRedStroke( 255 ),
92 mColorGreenStroke( 255 ),
93 mColorBlueStroke( 255 ),
98 mCurves.approximation_scale( 2.0 );
99 mContour.auto_detect_orientation(
false );
100 mConvStroke.line_join( agg::round_join );
101 mConvStroke.line_cap( agg::round_cap );
104 #if defined ( WIN32 )
171 wxPLDevAGG::~wxPLDevAGG()
185 void wxPLDevAGG::drawPath( drawPathFlag flag )
192 if ( mStrokeOpacity && mStrokeWidth > 0.0 )
194 mConvStroke.
width( mStrokeWidth );
195 mRasterizer.add_path( mStrokeTransform );
196 mRendererSolid.color( agg::rgba8( mColorRedStroke, mColorGreenStroke, mColorBlueStroke, mStrokeOpacity ) );
197 agg::render_scanlines( mRasterizer, mScanLine, mRendererSolid );
201 if ( mStrokeOpacity )
203 mRasterizer.add_path( mPathTransform );
204 mRendererSolid.color( agg::rgba8( mColorRedStroke, mColorGreenStroke, mColorBlueStroke, mStrokeOpacity ) );
205 agg::render_scanlines( mRasterizer, mScanLine, mRendererSolid );
208 if ( mStrokeOpacity && mStrokeWidth > 0.0 )
210 mConvStroke.width( mStrokeWidth );
211 mRasterizer.add_path( mStrokeTransform );
212 mRendererSolid.color( agg::rgba8( mColorRedStroke, mColorGreenStroke, mColorBlueStroke, mStrokeOpacity ) );
213 agg::render_scanlines( mRasterizer, mScanLine, mRendererSolid );
225 void wxPLDevAGG::DrawLine(
short x1a,
short y1a,
short x2a,
short y2a )
228 mPath.move_to( x1a, y1a );
229 mPath.line_to( x2a, y2a );
231 if ( !resizing && ownGUI )
232 AGGAddtoClipRegion( x1a, y1a, x2a, y2a );
243 void wxPLDevAGG::DrawPolyline(
short *xa,
short *ya,
PLINT npts )
246 mPath.move_to( xa[0], ya[0] );
247 for (
PLINT i = 1; i < npts; i++ )
249 mPath.line_to( xa[i], ya[i] );
250 if ( !resizing && ownGUI )
251 AGGAddtoClipRegion( xa[i - 1], ya[i - 1], xa[i], ya[i] );
266 if ( x1 < 0 && y1 < 0 && x2 < 0 && y2 < 0 )
268 mRendererBase.clear( agg::rgba8( bgr, bgg, bgb ) );
269 if ( !resizing && ownGUI )
270 AddtoClipRegion( 0, 0, width, height );
275 mPath.move_to( x1, y1 );
276 mPath.line_to( x2, y1 );
277 mPath.line_to( x2, y2 );
278 mPath.line_to( x1, y2 );
279 mPath.close_polygon();
282 mRasterizer.add_path( mPathTransform );
283 mRendererSolid.color( agg::rgba8( bgr, bgg, bgb, 255 ) );
284 agg::render_scanlines( mRasterizer, mScanLine, mRendererSolid );
286 mConvStroke.width( 1.0 );
287 mRasterizer.add_path( mStrokeTransform );
288 mRendererSolid.color( agg::rgba8( bgr, bgg, bgb, 255 ) );
289 agg::render_scanlines( mRasterizer, mScanLine, mRendererSolid );
291 if ( !resizing && ownGUI )
292 AGGAddtoClipRegion( x1, y1, x2, y2 );
304 void wxPLDevAGG::AGGAddtoClipRegion(
short x1,
short y1,
short x2,
short y2 )
306 double x1d = x1, x2d = x2, y1d = y1, y2d = y2;
308 mTransform.transform( &x1d, &y1d );
309 mTransform.transform( &x2d, &y2d );
310 AddtoClipRegion( (
int) floor( x1d ), (
int) floor( y1d ), (
int) ceil( x2d ), (
int) ceil( y2d ) );
319 void wxPLDevAGG::FillPolygon(
PLStream *pls )
321 short *xa = pls->
dev_x;
322 short *ya = pls->
dev_y;
325 mPath.move_to( xa[0], ya[0] );
328 mPath.line_to( xa[i], ya[i] );
329 if ( !resizing && ownGUI )
330 AGGAddtoClipRegion( xa[i - 1], ya[i - 1], xa[i], ya[i] );
332 mPath.line_to( xa[0], ya[0] );
333 mPath.close_polygon();
335 drawPath( FillAndStroke );
345 void wxPLDevAGG::BlitRectangle( wxDC* dc,
int vX,
int vY,
int vW,
int vH )
350 wxBitmap bitmap( mBuffer->GetSubImage( wxRect( vX, vY, vW, vH ) ), -1 );
351 MemoryDC.SelectObject( bitmap );
352 dc->Blit( vX, vY, vW, vH, &MemoryDC, 0, 0 );
353 MemoryDC.SelectObject( wxNullBitmap );
363 void wxPLDevAGG::CreateCanvas()
370 mBuffer =
new wxImage( bm_width, bm_height );
371 mRenderingBuffer.attach( mBuffer->GetData(), bm_width, bm_height, bm_width * 3 );
374 mRenderingBuffer.attach( mBuffer->GetData(), width, height, width * 3 );
376 mRendererBase.reset_clipping(
true );
378 mTransform.premultiply( agg::trans_affine_translation( 0.0, height ) );
379 mTransform.premultiply( agg::trans_affine_scaling( 1.0 / scalex, -1.0 / scaley ) );
380 mStrokeWidth = ( scalex + scaley ) / 2.0;
389 void wxPLDevAGG::SetWidth(
PLStream *pls )
391 mStrokeWidth = ( scalex + scaley ) / 2.0 * ( pls->
width > 0 ? pls->
width : 1 );
400 void wxPLDevAGG::SetColor0(
PLStream *pls )
405 mStrokeOpacity = (wxUint8) ( pls->
curcolor.
a * 255 );
414 void wxPLDevAGG::SetColor1(
PLStream *pls )
419 mStrokeOpacity = (wxUint8) ( pls->
curcolor.
a * 255 );
429 void wxPLDevAGG::SetExternalBuffer(
void* image )
431 mBuffer = (wxImage *) image;
432 mRenderingBuffer.attach( mBuffer->GetData(), width, height, width * 3 );
434 mRendererBase.reset_clipping(
true );
436 mTransform.premultiply( agg::trans_affine_translation( 0.0, height ) );
437 mTransform.premultiply( agg::trans_affine_scaling( 1.0 / scalex, -1.0 / scaley ) );
438 mStrokeWidth = ( scalex + scaley ) / 2.0;
445 #ifdef PL_HAVE_FREETYPE
452 void wxPLDevAGG::PutPixel(
short x,
short y,
PLINT color )
454 mBuffer->SetRGB( x, y, GetRValue( color ), GetGValue( color ), GetBValue( color ) );
455 AddtoClipRegion( x, y, x, y );
464 void wxPLDevAGG::PutPixel(
short x,
short y )
466 mBuffer->SetRGB( x, y, mColorRedStroke, mColorGreenStroke, mColorBlueStroke );
467 AddtoClipRegion( x, y, x, y );
476 PLINT wxPLDevAGG::GetPixel(
short x,
short y )
478 return RGB( mBuffer->GetRed( x, y ), mBuffer->GetGreen( x, y ), mBuffer->GetBlue( x, y ) );
481 #endif // PL_HAVE_FREETYPE
484 void wxPLDevAGG::PSDrawTextToDC(
char* utf8_string,
bool drawText )
487 printf(
"utf8_string=%s\n", utf8_string );
489 double start_x = 0.0;
490 double start_y = 0.0;
494 size_t len = strlen( utf8_string );
495 char * str = utf8_string;
496 printf(
"len=%lu\n", (
unsigned long) len );
498 const agg::glyph_cache* glyph;
504 char * saveStr = str;
505 while ( *str && len )
507 glyph = mFontManager.glyph( *str );
511 mFontManager.add_kerning( &x, &y );
512 x += glyph->advance_x;
513 y += glyph->advance_y;
516 textHeight = textHeight > ( glyph->bounds.y2 - glyph->bounds.y1 + yOffset ) ?
517 textHeight : ( glyph->bounds.y2 - glyph->bounds.y1 + yOffset );
521 printf(
"str: %s, textWidth=%lf\n", saveStr, textWidth );
525 for (
size_t i = 0; i < len && str[i]; i++ )
527 glyph = mFontManager.glyph( str[i] );
530 printf(
"before: start_x=%f, start_y=%f\n", start_x, start_y );
532 mFontManager.add_kerning( &start_x, &start_y );
533 printf(
"after: start_x=%f, start_y=%f\n", start_x, start_y );
534 mFontManager.init_embedded_adaptors( glyph, start_x, start_y );
536 mRendererSolid.color( agg::rgba8( mColorRedStroke, mColorGreenStroke, mColorBlueStroke, mStrokeOpacity ) );
537 agg::render_scanlines( mFontManager.gray8_adaptor(), mFontManager.gray8_scanline(), mRendererSolid );
539 start_x += glyph->advance_x / scalex;
545 memset( utf8_string,
'\0', max_string_length );
549 void wxPLDevAGG::PSSetFont(
PLUNICODE fci )
554 if ( !mFontEngine.load_font(
"/usr/share/fonts/truetype/freefont/FreeSans.ttf", 0, agg::glyph_ren_agg_gray8 ) )
555 plabort(
"Font could not be loaded" );
557 mFontEngine.height( fontSize * fontScale );
558 mFontEngine.width( fontSize * fontScale );
559 mFontEngine.hinting(
true );
560 mFontEngine.flip_y(
false );
561 mContour.width( fontSize * fontScale * 0.2 );
567 plabort(
"The AGG backend can't process the text yet own its own!" );
572 printf(
"Non unicode string passed to a wxWidgets driver, ignoring\n" );
579 printf(
"Sorry, the wxWidgets drivers only handles strings of length < %d\n", 500 );
589 cos_shear = cos( shear );
590 sin_shear = sin( shear );
593 printf(
"textWidth=%f, textHeight=%f\n", textWidth, textHeight );
595 agg::trans_affine mtx;
597 mtx *= agg::trans_affine_translation( args->
x, args->
y );
601 mtx *= agg::trans_affine_translation( -args->
just * textWidth / scalex, -0.5 * textHeight );
602 mtx *= agg::trans_affine_translation( -args->
just * textWidth / scalex, -0.5 * textHeight );
603 mFontEngine.transform( mtx );
607 AddtoClipRegion( 0, 0, width, height );