Пример #1
0
wxBitmap ConvertTo24Bit( wxColor bgColor, wxBitmap front ) {
    if( front.GetDepth() == 24 ) return front;

    wxBitmap result( front.GetWidth(), front.GetHeight(), 24 );
    front.UseAlpha();

    wxImage im_front = front.ConvertToImage();
    wxImage im_result = result.ConvertToImage();

    unsigned char *presult = im_result.GetData();
    unsigned char *pfront = im_front.GetData();

    unsigned char *afront = NULL;
    if( im_front.HasAlpha() )
        afront = im_front.GetAlpha();

    for( int i = 0; i < result.GetWidth(); i++ ) {
        for( int j = 0; j < result.GetHeight(); j++ ) {

            double alphaF = (double) ( *afront++ ) / 256.0;
            unsigned char r = *pfront++ * alphaF + bgColor.Red() * ( 1.0 - alphaF );
            *presult++ = r;
            unsigned char g = *pfront++ * alphaF + bgColor.Green() * ( 1.0 - alphaF );
            *presult++ = g;
            unsigned char b = *pfront++ * alphaF + bgColor.Blue() * ( 1.0 - alphaF );
            *presult++ = b;
        }
    }

    result = wxBitmap( im_result );
    return result;
}
Пример #2
0
wxBitmap MergeBitmaps( wxBitmap back, wxBitmap front, wxSize offset )
{
    wxBitmap merged( back.GetWidth(), back.GetHeight(), back.GetDepth() );

    //  If the front bitmap has no alpha channel, then merging will accomplish nothing
    //  So, simply return the bitmap intact
    wxImage im_front = front.ConvertToImage();
    if(!im_front.HasAlpha())
        return front;
    
#if !wxCHECK_VERSION(2,9,4)

    // Manual alpha blending for broken wxWidgets alpha bitmap support, pervasive in wx2.8.
    merged.UseAlpha();
    back.UseAlpha();
    front.UseAlpha();

//    wxImage im_front = front.ConvertToImage();
    wxImage im_back = back.ConvertToImage();
    wxImage im_result = back.ConvertToImage();// Only way to make result have alpha channel in wxW 2.8.

    unsigned char *presult = im_result.GetData();
    unsigned char *pback = im_back.GetData();
    unsigned char *pfront = im_front.GetData();

    unsigned char *afront = NULL;
    if( im_front.HasAlpha() )
    afront = im_front.GetAlpha();

    unsigned char *aback = NULL;
    if( im_back.HasAlpha() )
    aback = im_back.GetAlpha();

    unsigned char *aresult = NULL;
    if( im_result.HasAlpha() )
    aresult = im_result.GetAlpha();

    // Do alpha blending, associative version of "over" operator.
    if(presult && pback && pfront){ 
        for( int i = 0; i < back.GetHeight(); i++ ) {
            for( int j = 0; j < back.GetWidth(); j++ ) {

                int fX = j - offset.x;
                int fY = i - offset.y;

                bool inFront = true;
                if( fX < 0 || fY < 0 ) inFront = false;
                if( fX >= front.GetWidth() ) inFront = false;
                if( fY >= front.GetHeight() ) inFront = false;

                if( inFront ) {
                    double alphaF = (double) ( *afront++ ) / 256.0;
                    double alphaB = (double) ( *aback++ ) / 256.0;
                    double alphaRes = alphaF + alphaB * ( 1.0 - alphaF );
                    unsigned char a = alphaRes * 256;
                    *aresult++ = a;
                    unsigned char r = (*pfront++ * alphaF + *pback++ * alphaB * ( 1.0 - alphaF )) / alphaRes;
                    *presult++ = r;
                    unsigned char g = (*pfront++ * alphaF + *pback++ * alphaB * ( 1.0 - alphaF )) / alphaRes;
                    *presult++ = g;
                    unsigned char b = (*pfront++ * alphaF + *pback++ * alphaB * ( 1.0 - alphaF )) / alphaRes;
                    *presult++ = b;
                } else {
                    *aresult++ = *aback++;
                    *presult++ = *pback++;
                    *presult++ = *pback++;
                    *presult++ = *pback++;
                }
            }
        }
    }
    merged = wxBitmap( im_result );

#else
    wxMemoryDC mdc( merged );
    mdc.DrawBitmap( back, 0, 0, true );
    mdc.DrawBitmap( front, offset.x, offset.y, true );
    mdc.SelectObject( wxNullBitmap );
#endif

    return merged;
}
Пример #3
0
wxBitmap MergeBitmaps( wxBitmap back, wxBitmap front, wxSize offset )
{
    wxBitmap merged( back.GetWidth(), back.GetHeight(), back.GetDepth() );
#if (defined(__WXGTK__) || defined(__WXMAC__))

    // Manual alpha blending for broken wxWidgets platforms.

    merged.UseAlpha();
    back.UseAlpha();
    front.UseAlpha();

    wxImage im_front = front.ConvertToImage();
    wxImage im_back = back.ConvertToImage();
    wxImage im_result = back.ConvertToImage();// Only way to make result have alpha channel in wxW 2.8.

    unsigned char *presult = im_result.GetData();
    unsigned char *pback = im_back.GetData();
    unsigned char *pfront = im_front.GetData();

    unsigned char *afront = NULL;
    if( im_front.HasAlpha() )
        afront = im_front.GetAlpha();

    unsigned char *aback = NULL;
    if( im_back.HasAlpha() )
        aback = im_back.GetAlpha();

    unsigned char *aresult = NULL;
    if( im_result.HasAlpha() )
        aresult = im_result.GetAlpha();

    // Do alpha blending, associative version of "over" operator.

    for( int i = 0; i < back.GetHeight(); i++ ) {
        for( int j = 0; j < back.GetWidth(); j++ ) {

            int fX = j - offset.x;
            int fY = i - offset.y;

            bool inFront = true;
            if( fX < 0 || fY < 0 ) inFront = false;
            if( fX >= front.GetWidth() ) inFront = false;
            if( fY >= front.GetHeight() ) inFront = false;

            if( inFront ) {
                double alphaF = (double) ( *afront++ ) / 256.0;
                double alphaB = (double) ( *aback++ ) / 256.0;
                double alphaRes = alphaF + alphaB * ( 1.0 - alphaF );
                unsigned char a = alphaRes * 256;
                *aresult++ = a;
                unsigned char r = (*pfront++ * alphaF + *pback++ * alphaB * ( 1.0 - alphaF )) / alphaRes;
                *presult++ = r;
                unsigned char g = (*pfront++ * alphaF + *pback++ * alphaB * ( 1.0 - alphaF )) / alphaRes;
                *presult++ = g;
                unsigned char b = (*pfront++ * alphaF + *pback++ * alphaB * ( 1.0 - alphaF )) / alphaRes;
                *presult++ = b;
            } else {
                *aresult++ = *aback++;
                *presult++ = *pback++;
                *presult++ = *pback++;
                *presult++ = *pback++;
            }
        }
    }

    merged = wxBitmap( im_result );

#else
    wxMemoryDC mdc( merged );
    mdc.DrawBitmap( back, 0, 0, true );
    mdc.DrawBitmap( front, offset.x, offset.y, true );
    mdc.SelectObject( wxNullBitmap );
#endif

    return merged;
}