X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/94803e4ec8d61d24ebf9b1e483776d17e55a7ec5..801423ee3454d200581cd51d35fbcdad19f2208a:/src/common/image.cpp diff --git a/src/common/image.cpp b/src/common/image.cpp index 89f35d5d57..6b431715c3 100644 --- a/src/common/image.cpp +++ b/src/common/image.cpp @@ -1089,35 +1089,60 @@ wxImage wxImage::Rotate90( bool clockwise ) const } unsigned char *data = image.GetData(); - const unsigned char *source_data = M_IMGDATA->m_data; unsigned char *target_data; - unsigned char *alpha_data = image.GetAlpha(); - const unsigned char *source_alpha = M_IMGDATA->m_alpha; - unsigned char *target_alpha = 0 ; - for (long j = 0; j < height; j++) + // we rotate the image in 21-pixel (63-byte) wide strips + // to make better use of cpu cache - memory transfers + // (note: while much better than single-pixel "strips", + // our vertical strips will still generally straddle cachelines) + for (long ii = 0; ii < width; ) { - for (long i = 0; i < width; i++) + long next_ii = wxMin(ii + 21, width); + + for (long j = 0; j < height; j++) { - if (clockwise) + const unsigned char *source_data + = M_IMGDATA->m_data + (j*width + ii)*3; + + for (long i = ii; i < next_ii; i++) { - target_data = data + (((i+1)*height) - j - 1)*3; - if (source_alpha) - target_alpha = alpha_data + (((i+1)*height) - j - 1); + if ( clockwise ) + { + target_data = data + (((i+1)*height) - j - 1)*3; + } + else + { + target_data = data + ((height*(width - 1 - i)) + j)*3; + } + memcpy( target_data, source_data, 3 ); + source_data += 3; } - else + } + + ii = next_ii; + } + + const unsigned char *source_alpha = M_IMGDATA->m_alpha; + + if ( source_alpha ) + { + unsigned char *alpha_data = image.GetAlpha(); + unsigned char *target_alpha = 0 ; + + for (long j = 0; j < height; j++) + { + for (long i = 0; i < width; i++) { - target_data = data + ((height*(width-1)) + j - (i*height))*3; - if (source_alpha) + if ( clockwise ) + { + target_alpha = alpha_data + (((i+1)*height) - j - 1); + } + else + { target_alpha = alpha_data + ((height*(width-1)) + j - (i*height)); - } - memcpy( target_data, source_data, 3 ); - source_data += 3; + } - if (source_alpha) - { - memcpy( target_alpha, source_alpha, 1 ); - source_alpha += 1; + *target_alpha = *source_alpha++; } } }