⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 algo2d.h

📁 手机游戏绘图类
💻 H
📖 第 1 页 / 共 2 页
字号:
//////////////////////////////////////////////////////////////////////////////
//
// PocketFrog - The Game Library for Pocket PC Devices
// Copyright 2002  Thierry Tremblay
//
// Permission to use, copy, modify, distribute and sell this software
// and its documentation for any purpose is hereby granted without fee,
// provided that the above copyright notice appear in all copies and
// that both that copyright notice and this permission notice appear
// in supporting documentation.  Thierry Tremblay makes no representations
// about the suitability of this software for any purpose.
// It is provided "as is" without express or implied warranty.
//
//////////////////////////////////////////////////////////////////////////////

#ifndef POCKETFROG_ALGO2D_H
#define POCKETFROG_ALGO2D_H

#include "../defs.h"
#include <PocketHAL/surface.h>

namespace Frog {
namespace Internal {



//////////////////////////////////////////////////////////////////////////////
//
// todo: STL stuff needed until the new shaders are in place
//
//////////////////////////////////////////////////////////////////////////////

template <class _InputIter, class _OutputIter, class _UnaryOperation>
inline _OutputIter 
transform( _InputIter __first, _InputIter __last,
           _OutputIter __result,
           _UnaryOperation __unary_op )
{
    for ( ; __first != __last; ++__first, ++__result)
        *__result = __unary_op( *__first );
    return __result;
}

template <class _InputIter1, class _InputIter2, class _OutputIter, class _BinaryOperation>
inline _OutputIter 
transform( _InputIter1 __first1, _InputIter1 __last1, 
           _InputIter2 __first2,
           _OutputIter __result,
           _BinaryOperation __binary_op )
{
    for ( ; __first1 != __last1; ++__first1, ++__first2, ++__result)
        *__result = __binary_op(*__first1, *__first2);
    return __result;
}


template <class _InputIter1, class _InputIter2, class _OutputIter, class _Predicate, class _BinaryOperation>
inline _OutputIter 
transform_if( _InputIter1 __first1, _InputIter1 __last1, 
              _InputIter2 __first2,
              _OutputIter __result,
              _Predicate __pred, _BinaryOperation __binary_op )
{
    for ( ; __first1 != __last1; ++__first1, ++__first2, ++__result)
        if (__pred(*__first1)) *__result = __binary_op(*__first1, *__first2);
    return __result;
}

template<class _A, class _R>
struct unary_function
{
	typedef _A argument_type;
	typedef _R result_type;
};

template<class _A1, class _A2, class _R>
	struct binary_function {
	typedef _A1 first_argument_type;
	typedef _A2 second_argument_type;
	typedef _R result_type;
	};

template<class _Bfn>
class binder1st
:   public unary_function<typename _Bfn::second_argument_type, typename _Bfn::result_type>
{
public:
	binder1st(const _Bfn& _X, const typename _Bfn::first_argument_type& _Y)
		: op(_X), value(_Y) {}
	result_type operator()(const argument_type& _X) const
		{return (op(value, _X)); }
protected:
	_Bfn op;
	typename _Bfn::first_argument_type value;
};



template<class _Bfn>
	class binder2nd
	: public unary_function<typename _Bfn::first_argument_type,
		typename _Bfn::result_type> {
public:
	binder2nd(const _Bfn& _X,
		const typename _Bfn::second_argument_type& _Y)
		: op(_X), value(_Y) {}
	result_type operator()(const argument_type& _X) const
		{return (op(_X, value)); }
protected:
	_Bfn op;
	typename _Bfn::second_argument_type value;
	};


template<class _Bfn, class _Ty> inline
	binder2nd<_Bfn> bind2nd(const _Bfn& _X, const _Ty& _Y)
		{return (binder2nd<_Bfn>(_X,
			_Bfn::second_argument_type(_Y))); }


template<class _Bfn, class _Ty> inline
	binder1st<_Bfn> bind1st(const _Bfn& _X, const _Ty& _Y)
		{
            return (binder1st<_Bfn>(_X, _Bfn::first_argument_type(_Y)));
        }

template<class _Ty>
	struct not_equal_to : binary_function<_Ty, _Ty, bool> {
	bool operator()(const _Ty& _X, const _Ty& _Y) const
		{return (_X != _Y); }
	};


namespace Algo2D {

//////////////////////////////////////////////////////////////////////////////
//
// 2D Raster Algorithms
//
//////////////////////////////////////////////////////////////////////////////

template<typename PixelFunction> inline
void Blit( PixelFunction& F, PHAL::Surface& buffer, const Rect& destRect, const PHAL::Surface& source, const Rect& srcRect )
{

    const Pixel* pSrc  = source.GetPixels( srcRect.left, srcRect.top );
    Pixel*       pDest = buffer.GetPixels( destRect.left, destRect.top );
    int          width = srcRect.GetWidth();

    for ( int h = srcRect.GetHeight(); h; --h )
    {
        transform( pSrc, pSrc + width, pDest, pDest, F );
        
        pSrc  = (Pixel*)((uint8_t*)pSrc + source.GetPitch());
        pDest = (Pixel*)((uint8_t*)pDest + buffer.GetPitch());
    }
}



template<typename PixelFunction> inline
void BlitMask( PixelFunction& F, PHAL::Surface& buffer, const Rect& destRect, const PHAL::Surface& source, const Rect& srcRect, Pixel mask )
{
    const Pixel* pSrc  = source.GetPixels( srcRect.left, srcRect.top );
    Pixel*       pDest = buffer.GetPixels( destRect.left, destRect.top );
    int          width = srcRect.GetWidth();

    for ( int h = srcRect.GetHeight(); h; --h )
    {
        transform_if( pSrc, pSrc + width, pDest, pDest, bind2nd( not_equal_to<Pixel>(), mask ), F );
        
        pSrc  = (Pixel*)((uint8_t*)pSrc + source.GetPitch());
        pDest = (Pixel*)((uint8_t*)pDest + buffer.GetPitch());
    }
}



template<typename PixelFunction> inline
void BlitTransform( PixelFunction& F, PHAL::Surface& buffer, const Rect& destRect, const unsigned transform[3][2], const PHAL::Surface& source )
{
    unsigned y1 = (destRect.top << 6) + (1<<5);
    unsigned y2 = (destRect.bottom << 6) + (1<<5);
    unsigned x1 = (destRect.left << 6) + (1<<5);
    unsigned x2 = (destRect.right << 6) + (1<<5);

    unsigned u0 = x1 * transform[0][0] + y1 * transform[1][0] + transform[2][0];
    unsigned v0 = x1 * transform[0][1] + y1 * transform[1][1] + transform[2][1];

    unsigned dudx = transform[0][0] << 6;
    unsigned dvdx = transform[0][1] << 6;
    unsigned dudy = transform[1][0] << 6;
    unsigned dvdy = transform[1][1] << 6;

    for (unsigned dy = y1; dy != y2; dy += (1<<6) )
    {
        Pixel* dest = buffer.GetPixels( x1 >> 6, dy >> 6 );

        unsigned u = u0;
        unsigned v = v0;

        for (unsigned dx = x1; dx != x2; dx += (1<<6) )
        {
            unsigned ix = u >> 16;
            unsigned iy = v >> 16;
            
            if (ix < (unsigned)source.GetWidth() && iy < (unsigned)source.GetHeight() )
            {
                *dest = F( *source.GetPixels(ix,iy), *dest );
            }

            u += dudx;
            v += dvdx;
            ++dest;
        }

        u0 += dudy;
        v0 += dvdy;
    }
}



template<typename PixelFunction> inline
void BlitTransformMask( PixelFunction& F, PHAL::Surface& buffer, const Rect& destRect, const unsigned transform[3][2], const PHAL::Surface& source, Pixel mask )
{
    unsigned y1 = (destRect.top << 6) + (1<<5);
    unsigned y2 = (destRect.bottom << 6) + (1<<5);
    unsigned x1 = (destRect.left << 6) + (1<<5);
    unsigned x2 = (destRect.right << 6) + (1<<5);

    unsigned u0 = x1 * transform[0][0] + y1 * transform[1][0] + transform[2][0];
    unsigned v0 = x1 * transform[0][1] + y1 * transform[1][1] + transform[2][1];

    unsigned dudx = transform[0][0] << 6;
    unsigned dvdx = transform[0][1] << 6;
    unsigned dudy = transform[1][0] << 6;
    unsigned dvdy = transform[1][1] << 6;

    for (unsigned dy = y1; dy != y2; dy += (1<<6) )
    {
        Pixel* dest = buffer.GetPixels( x1 >> 6, dy >> 6 );

        unsigned u = u0;
        unsigned v = v0;

        for (unsigned dx = x1; dx != x2; dx += (1<<6) )
        {
            unsigned ix = u >> 16;
            unsigned iy = v >> 16;
            
            if (ix < (unsigned)source.GetWidth() && iy < (unsigned)source.GetHeight() )
            {
                const Pixel& src = *source.GetPixels(ix,iy);

                if (src != mask)
                {
                    *dest = F( src, *dest );
                }
            }

            u += dudx;
            v += dvdx;
            ++dest;
        }

        u0 += dudy;
        v0 += dvdy;
    }
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -