2 * Kimikage NScripter Plugins Project
\r
4 * This software is distributed under a BSD-style license.
\r
5 * See license.txt for more information.
\r
8 #include "Decorator.h"
\r
13 Decorator::Decorator( void )
\r
15 face1 = Color( 0xFFFFFFFF );
\r
18 Decorator::~Decorator( void )
\r
22 void Decorator::setFace( const Color color )
\r
28 void Decorator::setEdge( const double width, const Color color )
\r
35 // +-+-+---+---+---+
\r
36 // --+0,0+1,0+2,0+3,0+---->
\r
37 // +-:-+---+---+---+
\r
41 //
\83e
\81[
\83u
\83\8b\8f\89\8aú
\89»
\r
42 //
\90³
\95û
\8c`
\82Å
\82 \82é
\82±
\82Æ
\82ð
\91O
\92ñ
\r
43 const size_t tableSize = sizeof( edgePower ) / sizeof( edgePower[0] );
\r
44 for( size_t j = 0; j < tableSize; ++j )
\r
46 for( size_t i = 0; i < tableSize; ++i )
\r
48 edgePower[j][i] = 0;
\r
52 if ( width <= 1e-20 )
\r
59 exTop = exBottom = exLeft = exRight = static_cast<unsigned int>( std::ceil( edgeWidth ) );
\r
61 const double r = width + rEqu; //
\89~
\82Ì
\94¼
\8ca
\r
62 const double s = rPi * r * r; //
\89~
\82Ì
\96Ê
\90Ï
\r
63 const double scale( edge1.getA() );
\r
64 if ( r <= rSqrt0_5 ) // (0.5,0.5)
\93\9e\92B
\82Ü
\82Å
\r
66 // a0 = SQRT(r^2-0.5^2) * 2 + 2*r^2*(
\r
67 // ASIN(0.5/r)-ACOS(0.5/r)
\r
68 // + 0.5*SIN(2*ASIN(0.5/r))-0.5*SIN(2*ACOS(0.5/r))
\r
70 const double a0 = 1.0 - 4.333 * (r - rSqrt0_5) * (r - rSqrt0_5); //2
\8e\9f\8bß
\8e\97\r
71 const double a1 = 0.25 * (s - a0);
\r
72 edgePower[0][0] = static_cast<int>( a0 * scale );
\r
73 edgePower[1][0] = static_cast<int>( a1 * scale );
\r
74 edgePower[1][1] = 0;
\r
77 if ( r <= 1.5 ) // (1.5,0.0)
\93\9e\92B
\82Ü
\82Å
\r
79 // b0 = 0.5*SQRT(r^2-0.5^2)-0.5+r^2*ASIN(0.5/r)
\r
81 const double b0 = 1.0422359371 * r - 0.5878914747; //1
\8e\9f\8bß
\8e\97\r
82 const double b1 = 0.25 * (s - 1.0) - b0;
\r
83 edgePower[0][0] = static_cast<int>( scale );
\r
84 edgePower[1][0] = static_cast<int>( b0 * scale );
\r
85 edgePower[1][1] = static_cast<int>( b1 * scale );
\r
91 void Decorator::drawFace( int x, int y, ArgbBitmap &bmp, const Glyph &glyph ) const
\r
93 if ( glyph.getBufferSize() <= 0 ) return;
\r
95 drawCoreSimple( x, y, bmp, glyph, face1 );
\r
98 void Decorator::drawCoreSimple( int x, int y, ArgbBitmap &bmp, const Glyph &glyph, const Color color ) const
\r
100 //
\8a®
\91S
\82É
\93§
\96¾
\82È
\82ç
\95`
\89æ
\82µ
\82È
\82¢
\r
101 if ( color.getA() == 0 ) return;
\r
107 unsigned char *src = clip( x, y, width, height, bmp, glyph );
\r
109 for( int j = 0; j < height; ++j )
\r
111 ArgbArray dest = bmp.getArray( x, y + j );
\r
112 for( int i = 0; i < width; ++i )
\r
114 if ( src[i] == 0 ) continue;
\r
115 const Color face( color.getArgb(), blend.mul( color.getA(), src[i] ) );
\r
116 dest[i] = blend.merge( dest[i], face );
\r
118 src += glyph.getPitch();
\r
122 void Decorator::drawEdge( int x, int y, ArgbBitmap &bmp, const Glyph &glyph ) const
\r
124 if ( glyph.getBufferSize() <= 0 ) return;
\r
126 const Color c00( edge1.getArgb(), edgePower[0][0] );
\r
127 const Color c10( edge1.getArgb(), edgePower[1][0] );
\r
128 const Color c11( edge1.getArgb(), edgePower[1][1] );
\r
130 drawCoreSimple( x-1, y-1, bmp, glyph, c11 ); //
\8d¶
\8fã
\r
131 drawCoreSimple( x+0, y-1, bmp, glyph, c10 ); //
\92\86\8fã
\r
132 drawCoreSimple( x+1, y-1, bmp, glyph, c11 ); //
\89E
\8fã
\r
133 drawCoreSimple( x-1, y+0, bmp, glyph, c10 ); //
\8d¶
\92\86\r
134 drawCoreSimple( x+0, y+0, bmp, glyph, c00 ); //
\92\86\92\86\r
135 drawCoreSimple( x+1, y+0, bmp, glyph, c10 ); //
\89E
\92\86\r
136 drawCoreSimple( x-1, y+1, bmp, glyph, c11 ); //
\8d¶
\89º
\r
137 drawCoreSimple( x+0, y+1, bmp, glyph, c10 ); //
\92\86\89º
\r
138 drawCoreSimple( x+1, y+1, bmp, glyph, c11 ); //
\89E
\89º
\r
139 if ( edgePower[2][0] > 0 )
\r
146 unsigned char *Decorator::clip( int &x, int &y, int &width, int &height,
\r
147 const ArgbBitmap &bmp, const Glyph&glyph ) const
\r
149 width = glyph.getWidth();
\r
150 height = glyph.getHeight();
\r
151 unsigned char *src = glyph.getBuffer();
\r
153 if ( x < 0 ) //(
\8d¶
\82É
\82Í
\82Ý
\8fo
\82Ä
\82¢
\82é)
\r
159 if ( y < 0 ) //(
\8fã
\82É
\82Í
\82Ý
\8fo
\82Ä
\82¢
\82é)
\r
162 src -= y * glyph.getPitch();
\r
165 if ( x + width > bmp.getWidth() ) //(
\89E
\82É
\82Í
\82Ý
\8fo
\82Ä
\82¢
\82é)
\r
167 width = bmp.getWidth() - x;
\r
169 if ( y + height > bmp.getHeight() ) //(
\89º
\82É
\82Í
\82Ý
\8fo
\82Ä
\82¢
\82é)
\r
171 height = bmp.getHeight() - y;
\r
177 const double Decorator::rPi( 3.14159265358979323846 ); // pi
\r
178 const double Decorator::rEqu( 0.564189583547756286948 ); // sqrt( 1 / pi )
\r
179 const double Decorator::rSqrt0_5( 0.7071067811865475244 ); // sqrt( 0.5 )
\r