diff options
| -rw-r--r-- | graphics/transparent_surface.cpp | 52 | ||||
| -rw-r--r-- | graphics/transparent_surface.h | 3 | 
2 files changed, 36 insertions, 19 deletions
| diff --git a/graphics/transparent_surface.cpp b/graphics/transparent_surface.cpp index 48e6da6c79..83869cef30 100644 --- a/graphics/transparent_surface.cpp +++ b/graphics/transparent_surface.cpp @@ -793,21 +793,17 @@ TransparentSurface *TransparentSurface::rotoscaleT(const TransformStruct &transf  template <TFilteringMode filteringMode>  TransparentSurface *TransparentSurface::scaleT(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); - -	int srcW = srcRect.width(); -	int srcH = srcRect.height(); -	int dstW = dstRect.width(); -	int dstH = dstRect.height(); +	int srcW = w; +	int srcH = h; +	int dstW = newWidth; +	int dstH = newHeight; -	target->create((uint16)dstW, (uint16)dstH, this->format); +	target->create((uint16)dstW, (uint16)dstH, format);  	if (filteringMode == FILTER_BILINEAR) { +		assert(format.bytesPerPixel == 4);  		bool flipx = false, flipy = false; // TODO: See mirroring comment in RenderTicket ctor @@ -954,25 +950,29 @@ TransparentSurface *TransparentSurface::scaleT(uint16 newWidth, uint16 newHeight  		delete[] say;  	} else { -  		int *scaleCacheX = new int[dstW];  		for (int x = 0; x < dstW; x++) {  			scaleCacheX[x] = (x * srcW) / dstW;  		} -		for (int y = 0; y < dstH; y++) { -			uint32 *destP = (uint32 *)target->getBasePtr(0, y); -			const uint32 *srcP = (const uint32 *)getBasePtr(0, (y * srcH) / dstH); -			for (int x = 0; x < dstW; x++) { -				*destP++ = srcP[scaleCacheX[x]]; -			} +		switch (format.bytesPerPixel) { +		case 1: +			scaleNN<uint8>(scaleCacheX, target); +			break; +		case 2: +			scaleNN<uint16>(scaleCacheX, target); +			break; +		case 4: +			scaleNN<uint32>(scaleCacheX, target); +			break; +		default: +			error("Can only scale 8bpp, 16bpp, and 32bpp");  		} -		delete[] scaleCacheX; +		delete[] scaleCacheX;  	}  	return target; -  }  TransparentSurface *TransparentSurface::convertTo(const PixelFormat &dstFormat, const byte *palette) const { @@ -1053,12 +1053,26 @@ TransparentSurface *TransparentSurface::convertTo(const PixelFormat &dstFormat,  	return surface;  } +template <typename Size> +void TransparentSurface::scaleNN(int *scaleCacheX, TransparentSurface *target) const { +	for (int y = 0; y < target->h; y++) { +		Size *destP = (Size *)target->getBasePtr(0, y); +		const Size *srcP = (const Size *)getBasePtr(0, (y * h) / target->h); +		for (int x = 0; x < target->w; x++) { +			*destP++ = srcP[scaleCacheX[x]]; +		} +	} +}  template TransparentSurface *TransparentSurface::rotoscaleT<FILTER_NEAREST>(const TransformStruct &transform) const;  template TransparentSurface *TransparentSurface::rotoscaleT<FILTER_BILINEAR>(const TransformStruct &transform) const;  template TransparentSurface *TransparentSurface::scaleT<FILTER_NEAREST>(uint16 newWidth, uint16 newHeight) const;  template TransparentSurface *TransparentSurface::scaleT<FILTER_BILINEAR>(uint16 newWidth, uint16 newHeight) const; +template void TransparentSurface::scaleNN<uint8>(int *scaleCacheX, TransparentSurface *target) const; +template void TransparentSurface::scaleNN<uint16>(int *scaleCacheX, TransparentSurface *target) const; +template void TransparentSurface::scaleNN<uint32>(int *scaleCacheX, TransparentSurface *target) const; +  TransparentSurface *TransparentSurface::rotoscale(const TransformStruct &transform) const {  	return rotoscaleT<FILTER_BILINEAR>(transform);  } diff --git a/graphics/transparent_surface.h b/graphics/transparent_surface.h index 6fcdac1735..22fe04551e 100644 --- a/graphics/transparent_surface.h +++ b/graphics/transparent_surface.h @@ -150,6 +150,7 @@ struct TransparentSurface : public Graphics::Surface {  	TransparentSurface *scaleT(uint16 newWidth, uint16 newHeight) const;  	TransparentSurface *scale(uint16 newWidth, uint16 newHeight) const; +  	/**  	 * @brief Rotoscale function; this returns a transformed version of this surface after rotation and  	 * scaling. Please do not use this if angle == 0, use plain old scaling function. @@ -176,6 +177,8 @@ struct TransparentSurface : public Graphics::Surface {  private:  	AlphaType _alphaMode; +	template <typename Size> +	void scaleNN(int *scaleCacheX, TransparentSurface *target) const;  };  /** | 
