diff options
| -rw-r--r-- | engines/wintermute/graphics/transform_struct.h | 26 | ||||
| -rw-r--r-- | engines/wintermute/graphics/transform_tools.cpp | 11 | ||||
| -rw-r--r-- | engines/wintermute/graphics/transform_tools.h | 6 | ||||
| -rw-r--r-- | engines/wintermute/graphics/transparent_surface.cpp | 211 | ||||
| -rw-r--r-- | engines/wintermute/graphics/transparent_surface.h | 6 | 
5 files changed, 129 insertions, 131 deletions
| diff --git a/engines/wintermute/graphics/transform_struct.h b/engines/wintermute/graphics/transform_struct.h index acde410e89..a54c4cc5d0 100644 --- a/engines/wintermute/graphics/transform_struct.h +++ b/engines/wintermute/graphics/transform_struct.h @@ -27,12 +27,12 @@  #include "engines/wintermute/dctypes.h"  namespace Wintermute { -/**  +/**   * Contains all the required information that define a transform.   * Same source sprite + same TransformStruct = Same resulting sprite.   * Has a number of overloaded constructors to accomodate various argument lists.   */ -	 +  const uint32 kDefaultZoomX = 100;  const uint32 kDefaultZoomY = 100;  const uint32 kDefaultRgbaMod = 0xFFFFFFFF; @@ -41,9 +41,9 @@ const int32 kDefaultHotspotY = 0;  const int32 kDefaultOffsetX = 0;  const int32 kDefaultOffsetY = 0;  const int32 kDefaultAngle = 0; -	 +  struct TransformStruct { -private:  +private:  	void init(Point32 zoom, uint32 angle, Point32 hotspot, bool alphaDisable, TSpriteBlendMode blendMode, uint32 alpha, bool mirrorX, bool mirrorY, Point32 offset);  public: @@ -51,16 +51,16 @@ public:  	TransformStruct(int32 zoomX, int32 zoomY, TSpriteBlendMode blendMode, uint32 alpha, bool mirrorX = false, bool mirrorY = false);  	TransformStruct(int32 zoomX, int32 zoomY, uint32 angle, int32 hotspotX = 0, int32 hotspotY = 0);  	TransformStruct(); -	 -	Point32 _zoom;	 ///< Zoom; 100 = no zoom + +	Point32 _zoom;   ///< Zoom; 100 = no zoom  	Point32 _hotspot; ///< Position of the hotspot -	uint32 _angle;	 ///< Rotation angle, in degrees -	byte _flip;		 ///< Bitflag: see TransparentSurface::FLIP_XXX +	uint32 _angle;   ///< Rotation angle, in degrees +	byte _flip;      ///< Bitflag: see TransparentSurface::FLIP_XXX  	bool _alphaDisable;  	TSpriteBlendMode _blendMode; -	uint32 _rgbaMod;	  ///< RGBa -	Point32 _offset;   -	 +	uint32 _rgbaMod;      ///< RGBa +	Point32 _offset; +  	bool getMirrorX() const;  	bool getMirrorY() const; @@ -72,9 +72,9 @@ public:  				compare._alphaDisable == _alphaDisable  &&  				compare._rgbaMod == _rgbaMod &&  				compare._blendMode == _blendMode -				); +			   );  	} -  +  	bool operator!=(const TransformStruct &compare) const {  		return !(compare == *this);  	} diff --git a/engines/wintermute/graphics/transform_tools.cpp b/engines/wintermute/graphics/transform_tools.cpp index 4f05e19a92..ebf9092aaa 100644 --- a/engines/wintermute/graphics/transform_tools.cpp +++ b/engines/wintermute/graphics/transform_tools.cpp @@ -25,7 +25,7 @@  #include <math.h>  namespace Wintermute { -	 +  FloatPoint TransformTools::transformPoint(const FloatPoint &point, const float rotate, const Point32 &zoom, const bool mirrorX, const bool mirrorY) {  	float rotateRad = rotate * M_PI / 180.0f;  	FloatPoint newPoint; @@ -40,20 +40,19 @@ FloatPoint TransformTools::transformPoint(const FloatPoint &point, const float r  	return newPoint;  } -Rect32 TransformTools::newRect (const Rect32 &oldRect, const TransformStruct &transform, Point32 *newHotspot) { - +Rect32 TransformTools::newRect(const Rect32 &oldRect, const TransformStruct &transform, Point32 *newHotspot) {  	Point32 nw(oldRect.left, oldRect.top);  	Point32 ne(oldRect.right, oldRect.top);  	Point32 sw(oldRect.left, oldRect.bottom);  	Point32 se(oldRect.right, oldRect.bottom); -		 +  	FloatPoint nw1, ne1, sw1, se1;  	nw1 = transformPoint(nw - transform._hotspot, transform._angle, transform._zoom);  	ne1 = transformPoint(ne - transform._hotspot, transform._angle, transform._zoom);  	sw1 = transformPoint(sw - transform._hotspot, transform._angle, transform._zoom);  	se1 = transformPoint(se - transform._hotspot, transform._angle, transform._zoom); -		 +  	float top = MIN(nw1.y, MIN(ne1.y, MIN(sw1.y, se1.y)));  	float bottom = MAX(nw1.y, MAX(ne1.y, MAX(sw1.y, se1.y)));  	float left = MIN(nw1.x, MIN(ne1.x, MIN(sw1.x, se1.x))); @@ -64,7 +63,7 @@ Rect32 TransformTools::newRect (const Rect32 &oldRect, const TransformStruct &tr  	newHotspot->x = (uint32)(-floor(left));  	res.top = (int32)(floor(top)) + transform._hotspot.y; -	res.bottom = (int32)(ceil(bottom)) + transform._hotspot.y;  +	res.bottom = (int32)(ceil(bottom)) + transform._hotspot.y;  	res.left = (int32)(floor(left)) + transform._hotspot.x;  	res.right = (int32)(ceil(right)) + transform._hotspot.x; diff --git a/engines/wintermute/graphics/transform_tools.h b/engines/wintermute/graphics/transform_tools.h index e59c47272a..c92b81fd11 100644 --- a/engines/wintermute/graphics/transform_tools.h +++ b/engines/wintermute/graphics/transform_tools.h @@ -30,10 +30,10 @@  namespace Wintermute {  class TransformTools { -public:	 +public:  	/**  	 * Basic transform (scale + rotate) for a single point -	 */	 +	 */  	static FloatPoint transformPoint(const FloatPoint &point, const float rotate, const Point32 &zoom, const bool mirrorX = false, const bool mirrorY = false);  	/** @@ -46,7 +46,7 @@ public:  	 * and, as a side-effect, "newHotspot" will tell you where the hotspot will  	 * have ended up in the new rect, for centering.  	 */ -	static Rect32 newRect (const Rect32 &oldRect, const TransformStruct &transform, Point32 *newHotspot);	 +	static Rect32 newRect(const Rect32 &oldRect, const TransformStruct &transform, Point32 *newHotspot);  };  } // End of namespace Wintermute diff --git a/engines/wintermute/graphics/transparent_surface.cpp b/engines/wintermute/graphics/transparent_surface.cpp index 3469bcbe1e..663c0ed01a 100644 --- a/engines/wintermute/graphics/transparent_surface.cpp +++ b/engines/wintermute/graphics/transparent_surface.cpp @@ -34,112 +34,111 @@ namespace Wintermute {  #if ENABLE_BILINEAR  void TransparentSurface::copyPixelBilinear(float projX, float projY, int dstX, int dstY, const Common::Rect &srcRect, const Common::Rect &dstRect, const TransparentSurface *src, TransparentSurface *dst) { +	int srcW = srcRect.width(); +	int srcH = srcRect.height(); +	int dstW = dstRect.width(); +	int dstH = dstRect.height(); -			int srcW = srcRect.width(); -			int srcH = srcRect.height(); -			int dstW = dstRect.width(); -			int dstH = dstRect.height(); +	assert(dstX >= 0 && dstX < dstW); +	assert(dstY >= 0 && dstY < dstH); -			assert(dstX >= 0 && dstX < dstW); -			assert(dstY >= 0 && dstY < dstH); +	float x1 = floor(projX); +	float x2 = ceil(projX); +	float y1 = floor(projY); +	float y2 = ceil(projY); -			float x1 = floor(projX); -			float x2 = ceil(projX); -			float y1 = floor(projY); -			float y2 = ceil(projY); +	uint32 Q11, Q12, Q21, Q22; -			uint32 Q11, Q12, Q21, Q22; +	if (x1 >= srcW || x1 < 0 || y1 >= srcH || y1 < 0) { +		Q11 = 0; +	} else { +		Q11 = READ_UINT32((const byte *)src->getBasePtr((int)(x1 + srcRect.left), (int)(y1 + srcRect.top))); +	} -			if (x1 >= srcW || x1 < 0 || y1 >= srcH || y1 < 0) {  -				Q11 = 0; -			} else { -				Q11 = READ_UINT32((const byte *)src->getBasePtr((int)(x1 + srcRect.left),(int)(y1 + srcRect.top))); -			} +	if (x1 >= srcW || x1 < 0 || y2 >= srcH || y2 < 0) { +		Q12 = 0; +	} else { +		Q12 = READ_UINT32((const byte *)src->getBasePtr((int)(x1 + srcRect.left), (int)(y2 + srcRect.top))); +	} -			if (x1 >= srcW || x1 < 0 || y2 >= srcH || y2 < 0) {  -				Q12 = 0; -			} else { -				Q12 = READ_UINT32((const byte *)src->getBasePtr((int)(x1 + srcRect.left), (int)(y2 + srcRect.top))); -			} +	if (x2 >= srcW || x2 < 0 || y1 >= srcH || y1 < 0) { +		Q21 = 0; +	} else { +		Q21 = READ_UINT32((const byte *)src->getBasePtr((int)(x2 + srcRect.left), (int)(y1 + srcRect.top))); +	} -			if (x2 >= srcW || x2 < 0 || y1 >= srcH || y1 < 0) {  -				Q21 = 0; -			} else { -				Q21 = READ_UINT32((const byte *)src->getBasePtr((int)(x2 + srcRect.left), (int)(y1 + srcRect.top))); -			} +	if (x2 >= srcW || x2 < 0 || y2 >= srcH || y2 < 0) { +		Q22 = 0; +	} else { +		Q22 = READ_UINT32((const byte *)src->getBasePtr((int)(x2 + srcRect.left), (int)(y2 + srcRect.top))); +	} -			if (x2 >= srcW || x2 < 0 || y2 >= srcH || y2 < 0) {  -				Q22 = 0; -			} else { -				Q22 = READ_UINT32((const byte *)src->getBasePtr((int)(x2 + srcRect.left), (int)(y2 + srcRect.top))); -			} +	byte *Q11s = (byte *)&Q11; +	byte *Q12s = (byte *)&Q12; +	byte *Q21s = (byte *)&Q21; +	byte *Q22s = (byte *)&Q22; -			byte *Q11s = (byte *)&Q11; -			byte *Q12s = (byte *)&Q12; -			byte *Q21s = (byte *)&Q21; -			byte *Q22s = (byte *)&Q22; - -			uint32 color; -			byte *dest = (byte *)&color; -			 -			float q11x = (x2 - projX); -			float q11y = (y2 - projY); -			float q21x = (projX - x1); -			float q21y = (y2 - projY); -			float q12x = (x2 - projX); -			float q12y = (projY - y1); - -			if (x1 == x2 && y1 == y2) { -				for (int c = 0; c < 4; c++) { -					dest[c]	= ((float)Q11s[c]); -				} -			} else { +	uint32 color; +	byte *dest = (byte *)&color; -				if (x1 == x2) {  -					q11x = 0.5;  -					q12x = 0.5;  -					q21x = 0.5;  -				} else if (y1 == y2) {  -					q11y = 0.5;  -					q12y = 0.5;  -					q21y = 0.5;  -				}  - -				for (int c = 0; c < 4; c++) { -					dest[c]	= (byte)( -								((float)Q11s[c]) * q11x * q11y + -								((float)Q21s[c]) * q21x * q21y + -								((float)Q12s[c]) * q12x * q12y + -								((float)Q22s[c]) * (1.0 -  -													 q11x * q11y -  -													 q21x * q21y -  -													 q12x * q12y) -							  ); -				}					 -			} -			WRITE_UINT32((byte *)dst->getBasePtr(dstX + dstRect.left, dstY + dstRect.top), color); +	float q11x = (x2 - projX); +	float q11y = (y2 - projY); +	float q21x = (projX - x1); +	float q21y = (y2 - projY); +	float q12x = (x2 - projX); +	float q12y = (projY - y1); + +	if (x1 == x2 && y1 == y2) { +		for (int c = 0; c < 4; c++) { +			dest[c] = ((float)Q11s[c]); +		} +	} else { + +		if (x1 == x2) { +			q11x = 0.5; +			q12x = 0.5; +			q21x = 0.5; +		} else if (y1 == y2) { +			q11y = 0.5; +			q12y = 0.5; +			q21y = 0.5; +		} + +		for (int c = 0; c < 4; c++) { +			dest[c] = (byte)( +						  ((float)Q11s[c]) * q11x * q11y + +						  ((float)Q21s[c]) * q21x * q21y + +						  ((float)Q12s[c]) * q12x * q12y + +						  ((float)Q22s[c]) * (1.0 - +											  q11x * q11y - +											  q21x * q21y - +											  q12x * q12y) +					  ); +		} +	} +	WRITE_UINT32((byte *)dst->getBasePtr(dstX + dstRect.left, dstY + dstRect.top), color);  }  #else  void TransparentSurface::copyPixelNearestNeighbor(float projX, float projY, int dstX, int dstY, const Common::Rect &srcRect, const Common::Rect &dstRect, const TransparentSurface *src, TransparentSurface *dst) { -			int srcW = srcRect.width(); -			int srcH = srcRect.height(); -			int dstW = dstRect.width(); -			int dstH = dstRect.height(); - -			assert(dstX >= 0 && dstX < dstW); -			assert(dstY >= 0 && dstY < dstH); - -			uint32 color; -			 -			if (projX >= srcW || projX < 0 || projY >= srcH || projY < 0) {  -				color = 0; -			} else { -				color = READ_UINT32((const byte *)src->getBasePtr((int)projX, (int)projY)); -			} +	int srcW = srcRect.width(); +	int srcH = srcRect.height(); +	int dstW = dstRect.width(); +	int dstH = dstRect.height(); + +	assert(dstX >= 0 && dstX < dstW); +	assert(dstY >= 0 && dstY < dstH); + +	uint32 color; + +	if (projX >= srcW || projX < 0 || projY >= srcH || projY < 0) { +		color = 0; +	} else { +		color = READ_UINT32((const byte *)src->getBasePtr((int)projX, (int)projY)); +	} - 			WRITE_UINT32((byte *)dst->getBasePtr(dstX, dstY), color); +	WRITE_UINT32((byte *)dst->getBasePtr(dstX, dstY), color);  } -#endif  +#endif  byte *TransparentSurface::_lookup = nullptr; @@ -162,7 +161,7 @@ TransparentSurface::TransparentSurface(const Surface &surf, bool copyData) : Sur  	}  } -void doBlitOpaque(byte *ino, byte* outo, uint32 width, uint32 height, uint32 pitch, int32 inStep, int32 inoStep) { +void doBlitOpaque(byte *ino, byte *outo, uint32 width, uint32 height, uint32 pitch, int32 inStep, int32 inoStep) {  	byte *in, *out;  #ifdef SCUMM_LITTLE_ENDIAN @@ -193,7 +192,7 @@ void TransparentSurface::generateLookup() {  	}  } -void TransparentSurface::doBlitAlpha(byte *ino, byte* outo, uint32 width, uint32 height, uint32 pitch, int32 inStep, int32 inoStep) { +void TransparentSurface::doBlitAlpha(byte *ino, byte *outo, uint32 width, uint32 height, uint32 pitch, int32 inStep, int32 inoStep) {  	byte *in, *out;  	if (!_lookup) { @@ -312,11 +311,11 @@ Common::Rect TransparentSurface::blit(Graphics::Surface &target, int posX, int p  		srcImage.h = pPartRect->height();  		debug(6, "Blit(%d, %d, %d, [%d, %d, %d, %d], %08x, %d, %d)", posX, posY, flipping, -		      pPartRect->left,  pPartRect->top, pPartRect->width(), pPartRect->height(), color, width, height); +			  pPartRect->left,  pPartRect->top, pPartRect->width(), pPartRect->height(), color, width, height);  	} else {  		debug(6, "Blit(%d, %d, %d, [%d, %d, %d, %d], %08x, %d, %d)", posX, posY, flipping, 0, 0, -		      srcImage.w, srcImage.h, color, width, height); +			  srcImage.w, srcImage.h, color, width, height);  	}  	if (width == -1) @@ -496,12 +495,12 @@ Common::Rect TransparentSurface::blit(Graphics::Surface &target, int posX, int p  }  TransparentSurface *TransparentSurface::rotoscale(const TransformStruct &transform) const { -	 +  	assert(transform._angle != 0); // This would not be ideal; rotoscale() should never be called in conditional branches where angle = 0 anyway.  	Point32 newHotspot;  	Common::Rect srcRect(0, 0, (int16)w, (int16)h); -	Rect32 rect = TransformTools::newRect(Rect32 (srcRect), transform, &newHotspot); +	Rect32 rect = TransformTools::newRect(Rect32(srcRect), transform, &newHotspot);  	Common::Rect dstRect(0, 0, (int16)(rect.right - rect.left), (int16)(rect.bottom - rect.top));  	TransparentSurface *target = new TransparentSurface(); @@ -523,16 +522,16 @@ TransparentSurface *TransparentSurface::rotoscale(const TransformStruct &transfo  			int x1 = x - newHotspot.x;  			int y1 = y - newHotspot.y; -			targX = ((x1 * invCos - y1 * invSin)) * kDefaultZoomX / transform._zoom.x + srcRect.left;  -			targY = ((x1 * invSin + y1 * invCos)) * kDefaultZoomY / transform._zoom.y + srcRect.top;  -				 +			targX = ((x1 * invCos - y1 * invSin)) * kDefaultZoomX / transform._zoom.x + srcRect.left; +			targY = ((x1 * invSin + y1 * invCos)) * kDefaultZoomY / transform._zoom.y + srcRect.top; +  			targX += transform._hotspot.x;  			targY += transform._hotspot.y; -			 +  #if ENABLE_BILINEAR -			copyPixelBilinear(targX, targY, x, y, srcRect, dstRect, this, target);  +			copyPixelBilinear(targX, targY, x, y, srcRect, dstRect, this, target);  #else -			copyPixelNearestNeighbor(targX, targY, x, y, srcRect, dstRect, this, target);  +			copyPixelNearestNeighbor(targX, targY, x, y, srcRect, dstRect, this, target);  #endif  		}  	} @@ -542,7 +541,7 @@ TransparentSurface *TransparentSurface::rotoscale(const TransformStruct &transfo  TransparentSurface *TransparentSurface::scale(uint16 newWidth, uint16 newHeight) const {  	Common::Rect srcRect(0, 0, (int16)w, (int16)h);  	Common::Rect dstRect(0, 0, (int16)newWidth, (int16)newHeight); -		 +  	TransparentSurface *target = new TransparentSurface();  	assert(format.bytesPerPixel == 4); @@ -562,9 +561,9 @@ TransparentSurface *TransparentSurface::scale(uint16 newWidth, uint16 newHeight)  			projX = x / (float)dstW * srcW;  			projY = y / (float)dstH * srcH;  #if ENABLE_BILINEAR -			copyPixelBilinear(projX, projY, x, y, srcRect, dstRect, this, target);  +			copyPixelBilinear(projX, projY, x, y, srcRect, dstRect, this, target);  #else -			copyPixelNearestNeighbor(projX, projY, x, y, srcRect, dstRect, this, target);  +			copyPixelNearestNeighbor(projX, projY, x, y, srcRect, dstRect, this, target);  #endif  		}  	} diff --git a/engines/wintermute/graphics/transparent_surface.h b/engines/wintermute/graphics/transparent_surface.h index f2a0c1852a..9d06f3e006 100644 --- a/engines/wintermute/graphics/transparent_surface.h +++ b/engines/wintermute/graphics/transparent_surface.h @@ -112,12 +112,12 @@ struct TransparentSurface : public Graphics::Surface {  	                  int width = -1, int height = -1);  	void applyColorKey(uint8 r, uint8 g, uint8 b, bool overwriteAlpha = false); -	TransparentSurface *scale (uint16 newWidth, uint16 newHeight) const; -	TransparentSurface *rotoscale (const TransformStruct &transform) const;   +	TransparentSurface *scale(uint16 newWidth, uint16 newHeight) const; +	TransparentSurface *rotoscale(const TransformStruct &transform) const;  	static byte *_lookup;  	static void destroyLookup();  private: -	static void doBlitAlpha(byte *ino, byte* outo, uint32 width, uint32 height, uint32 pitch, int32 inStep, int32 inoStep); +	static void doBlitAlpha(byte *ino, byte *outo, uint32 width, uint32 height, uint32 pitch, int32 inStep, int32 inoStep);  	static void generateLookup();  }; | 
