Changeset 59619 in webkit
- Timestamp:
- May 17, 2010 12:09:24 PM (14 years ago)
- Location:
- trunk/WebCore
- Files:
-
- 3 added
- 6 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/WebCore/ChangeLog
r59618 r59619 1 2010-05-17 Jakob Petsovits <jpetsovits@rim.com> 2 3 Reviewed by George Staikos. 4 5 [OpenVG] Add support for decoding and drawing images 6 https://bugs.webkit.org/show_bug.cgi?id=36072 7 8 OpenVG has a maximum image size (how large is 9 specific to the OpenVG implementation), so this 10 requires us to store them as separate image tiles. 11 12 Image decoding and initial drawing code by 13 Adam Treat <atreat@rim.com>. Image decoder 14 downsampling support by Yong Li <yoli@rim.com>. 15 16 * platform/graphics/ImageSource.h: 17 * platform/graphics/openvg/ImageOpenVG.cpp: Added. 18 (WebCore::FrameData::clear): 19 (WebCore::BitmapImage::BitmapImage): 20 (WebCore::BitmapImage::checkForSolidColor): 21 (WebCore::BitmapImage::initPlatformData): 22 (WebCore::BitmapImage::invalidatePlatformData): 23 (WebCore::adjustSourceRectForDownSampling): 24 (WebCore::BitmapImage::draw): 25 (WebCore::Image::drawPattern): 26 (WebCore::Image::loadPlatformResource): 27 * platform/graphics/openvg/PainterOpenVG.cpp: 28 (WebCore::PainterOpenVG::drawImage): 29 (WebCore::PainterOpenVG::asNewNativeImage): 30 * platform/graphics/openvg/PainterOpenVG.h: 31 * platform/graphics/openvg/TiledImageOpenVG.cpp: Added. 32 (WebCore::TiledImageOpenVG::TiledImageOpenVG): 33 (WebCore::TiledImageOpenVG::operator=): 34 (WebCore::TiledImageOpenVG::~TiledImageOpenVG): 35 (WebCore::TiledImageOpenVG::numTiles): 36 (WebCore::TiledImageOpenVG::numColumns): 37 (WebCore::TiledImageOpenVG::numRows): 38 (WebCore::TiledImageOpenVG::setTile): 39 (WebCore::TiledImageOpenVG::tilesInRect): 40 (WebCore::TiledImageOpenVG::tile): 41 (WebCore::TiledImageOpenVG::tileRect): 42 (WebCore::TiledImageOpenVG::detachTiles): 43 (WebCore::TiledImageOpenVG::destroyTiles): 44 * platform/graphics/openvg/TiledImageOpenVG.h: Added. 45 (WebCore::TiledImageOpenVG::size): 46 (WebCore::TiledImageOpenVG::maxTileSize): 47 * platform/graphics/openvg/VGUtils.cpp: 48 (WebCore::VGUtils::bytesForImage): 49 (WebCore::VGUtils::bytesForImageScanline): 50 (WebCore::VGUtils::imageFormatBitsPerPixel): 51 (WebCore::VGUtils::endianAwareImageFormat): 52 * platform/graphics/openvg/VGUtils.h: 53 * platform/image-decoders/openvg/ImageDecoderOpenVG.cpp: Added. 54 (WebCore::RGBA32Buffer::asNewNativeImage): 55 1 56 2010-05-17 Yaar Schnitman <yaar@chromium.org> 2 57 -
trunk/WebCore/platform/graphics/ImageSource.h
r52791 r59619 63 63 typedef CGImageSourceRef NativeImageSourcePtr; 64 64 typedef CGImageRef NativeImagePtr; 65 #elif PLATFORM(OPENVG) 66 class ImageDecoder; 67 class TiledImageOpenVG; 68 typedef ImageDecoder* NativeImageSourcePtr; 69 typedef TiledImageOpenVG* NativeImagePtr; 65 70 #elif PLATFORM(QT) 66 71 class ImageDecoderQt; -
trunk/WebCore/platform/graphics/openvg/PainterOpenVG.cpp
r55923 r59619 32 32 #include "PlatformPathOpenVG.h" 33 33 #include "SurfaceOpenVG.h" 34 #include "TiledImageOpenVG.h" 34 35 #include "VGUtils.h" 35 36 … … 1086 1087 } 1087 1088 1089 void PainterOpenVG::drawImage(TiledImageOpenVG* tiledImage, const FloatRect& dst, const FloatRect& src) 1090 { 1091 ASSERT(m_state); 1092 m_surface->makeCurrent(); 1093 1094 // If buffers can be larger than the maximum OpenVG image sizes, 1095 // we split them into tiles. 1096 IntRect drawnTiles = tiledImage->tilesInRect(src); 1097 AffineTransform srcToDstTransformation = makeMapBetweenRects( 1098 FloatRect(FloatPoint(0.0, 0.0), src.size()), dst); 1099 srcToDstTransformation.translate(-src.x(), -src.y()); 1100 1101 for (int yIndex = drawnTiles.y(); yIndex < drawnTiles.bottom(); ++yIndex) { 1102 for (int xIndex = drawnTiles.x(); xIndex < drawnTiles.right(); ++xIndex) { 1103 // The srcTile rectangle is an aligned tile cropped by the src rectangle. 1104 FloatRect tile(tiledImage->tileRect(xIndex, yIndex)); 1105 FloatRect srcTile = intersection(src, tile); 1106 1107 save(); 1108 1109 // If the image is drawn in full, all we need is the proper transformation 1110 // in order to get it drawn at the right spot on the surface. 1111 concatTransformation(AffineTransform(srcToDstTransformation).translate(tile.x(), tile.y())); 1112 1113 // If only a part of the tile is drawn, we also need to clip the surface. 1114 if (srcTile != tile) { 1115 // Put boundaries relative to tile origin, as we already 1116 // translated to (x, y) with the transformation matrix. 1117 srcTile.move(-tile.x(), -tile.y()); 1118 intersectClipRect(srcTile); 1119 } 1120 1121 VGImage image = tiledImage->tile(xIndex, yIndex); 1122 if (image != VG_INVALID_HANDLE) { 1123 vgDrawImage(image); 1124 ASSERT_VG_NO_ERROR(); 1125 } 1126 1127 restore(); 1128 } 1129 } 1130 } 1131 1088 1132 #ifdef OPENVG_VERSION_1_1 1089 1133 void PainterOpenVG::drawText(VGFont vgFont, Vector<VGuint>& characters, VGfloat* adjustmentsX, VGfloat* adjustmentsY, const FloatPoint& point) … … 1137 1181 } 1138 1182 #endif 1183 1184 TiledImageOpenVG* PainterOpenVG::asNewNativeImage(const IntRect& src, VGImageFormat format) 1185 { 1186 ASSERT(m_state); 1187 m_surface->sharedSurface()->makeCurrent(); 1188 1189 const IntSize vgMaxImageSize(vgGeti(VG_MAX_IMAGE_WIDTH), vgGeti(VG_MAX_IMAGE_HEIGHT)); 1190 ASSERT_VG_NO_ERROR(); 1191 1192 const IntRect rect = intersection(src, IntRect(0, 0, m_surface->width(), m_surface->height())); 1193 TiledImageOpenVG* tiledImage = new TiledImageOpenVG(rect.size(), vgMaxImageSize); 1194 1195 const int numColumns = tiledImage->numColumns(); 1196 const int numRows = tiledImage->numRows(); 1197 1198 // Create the images as resources of the shared surface/context. 1199 for (int yIndex = 0; yIndex < numRows; ++yIndex) { 1200 for (int xIndex = 0; xIndex < numColumns; ++xIndex) { 1201 IntRect tileRect = tiledImage->tileRect(xIndex, yIndex); 1202 VGImage image = vgCreateImage(format, tileRect.width(), tileRect.height(), VG_IMAGE_QUALITY_FASTER); 1203 ASSERT_VG_NO_ERROR(); 1204 1205 tiledImage->setTile(xIndex, yIndex, image); 1206 } 1207 } 1208 1209 // Fill the image contents with our own surface/context being current. 1210 m_surface->makeCurrent(); 1211 1212 for (int yIndex = 0; yIndex < numRows; ++yIndex) { 1213 for (int xIndex = 0; xIndex < numColumns; ++xIndex) { 1214 IntRect tileRect = tiledImage->tileRect(xIndex, yIndex); 1215 1216 vgGetPixels(tiledImage->tile(xIndex, yIndex), 0, 0, 1217 rect.x() + tileRect.x(), rect.y() + tileRect.y(), 1218 tileRect.width(), tileRect.height()); 1219 ASSERT_VG_NO_ERROR(); 1220 } 1221 } 1222 1223 return tiledImage; 1224 } 1139 1225 1140 1226 void PainterOpenVG::save(PainterOpenVG::SaveMode saveMode) -
trunk/WebCore/platform/graphics/openvg/PainterOpenVG.h
r55923 r59619 38 38 class Path; 39 39 class SurfaceOpenVG; 40 class TiledImageOpenVG; 40 41 41 42 struct PlatformPainterState; … … 102 103 void drawEllipse(const IntRect& bounds, VGbitfield paintModes = (VG_STROKE_PATH | VG_FILL_PATH)); 103 104 void drawPolygon(size_t numPoints, const FloatPoint* points, VGbitfield paintModes = (VG_STROKE_PATH | VG_FILL_PATH)); 105 void drawImage(TiledImageOpenVG*, const FloatRect& dst, const FloatRect& src); 104 106 #ifdef OPENVG_VERSION_1_1 105 107 void drawText(VGFont, Vector<VGuint>& characters, VGfloat* adjustmentsX, VGfloat* adjustmentsY, const FloatPoint&); … … 117 119 void intersectClipRect(const FloatRect&); 118 120 void clipPath(const Path&, PainterOpenVG::ClipOperation, WindRule clipRule = RULE_NONZERO); 121 122 TiledImageOpenVG* asNewNativeImage(const IntRect& src, VGImageFormat); 119 123 120 124 void save(PainterOpenVG::SaveMode saveMode = CreateNewState); -
trunk/WebCore/platform/graphics/openvg/VGUtils.cpp
r55369 r59619 121 121 } 122 122 123 } 123 int VGUtils::bytesForImage(VGImageFormat format, VGint width, VGint height) 124 { 125 return width * height * imageFormatBitsPerPixel(format) / 8; 126 } 127 128 int VGUtils::bytesForImageScanline(VGImageFormat format, VGint width) 129 { 130 int bits = width * imageFormatBitsPerPixel(format); 131 if (bits % 8 > 1) // If unaligned, round up to the next byte. 132 bits += 8 - (bits % 8); 133 134 return bits / 8; 135 } 136 137 int VGUtils::imageFormatBitsPerPixel(VGImageFormat format) 138 { 139 switch (format) { 140 case VG_sRGBX_8888: 141 case VG_sRGBA_8888: 142 case VG_sRGBA_8888_PRE: 143 case VG_lRGBX_8888: 144 case VG_lRGBA_8888: 145 case VG_lRGBA_8888_PRE: 146 case VG_sXRGB_8888: 147 case VG_sARGB_8888: 148 case VG_sARGB_8888_PRE: 149 case VG_lXRGB_8888: 150 case VG_lARGB_8888: 151 case VG_lARGB_8888_PRE: 152 case VG_sBGRX_8888: 153 case VG_sBGRA_8888: 154 case VG_sBGRA_8888_PRE: 155 case VG_lBGRX_8888: 156 case VG_lBGRA_8888: 157 case VG_lBGRA_8888_PRE: 158 case VG_sXBGR_8888: 159 case VG_sABGR_8888: 160 case VG_sABGR_8888_PRE: 161 case VG_lXBGR_8888: 162 case VG_lABGR_8888: 163 case VG_lABGR_8888_PRE: 164 return 32; 165 166 case VG_sRGB_565: 167 case VG_sRGBA_5551: 168 case VG_sRGBA_4444: 169 case VG_sARGB_1555: 170 case VG_sARGB_4444: 171 case VG_sBGR_565: 172 case VG_sBGRA_5551: 173 case VG_sBGRA_4444: 174 case VG_sABGR_1555: 175 case VG_sABGR_4444: 176 return 16; 177 178 case VG_sL_8: 179 case VG_lL_8: 180 case VG_A_8: 181 return 8; 182 183 case VG_A_4: 184 return 4; 185 186 case VG_BW_1: 187 case VG_A_1: 188 return 1; 189 190 default: // Will only happen when OpenVG extends the enum and we don't. 191 ASSERT(false); 192 return 0; 193 } 194 } 195 196 #ifndef WTF_PLATFORM_BIG_ENDIAN 197 VGImageFormat VGUtils::endianAwareImageFormat(VGImageFormat bigEndianFormat) 198 { 199 switch (bigEndianFormat) { 200 case VG_sRGBX_8888: return VG_sXBGR_8888; 201 case VG_sRGBA_8888: return VG_sABGR_8888; 202 case VG_sRGBA_8888_PRE: return VG_sABGR_8888_PRE; 203 case VG_lRGBX_8888: return VG_lXBGR_8888; 204 case VG_lRGBA_8888: return VG_lABGR_8888; 205 case VG_lRGBA_8888_PRE: return VG_lABGR_8888_PRE; 206 case VG_sXRGB_8888: return VG_sBGRX_8888; 207 case VG_sARGB_8888: return VG_sBGRA_8888; 208 case VG_sARGB_8888_PRE: return VG_sBGRA_8888_PRE; 209 case VG_lXRGB_8888: return VG_lBGRX_8888; 210 case VG_lARGB_8888: return VG_lBGRA_8888; 211 case VG_lARGB_8888_PRE: return VG_lBGRA_8888_PRE; 212 case VG_sBGRX_8888: return VG_sXRGB_8888; 213 case VG_sBGRA_8888: return VG_sARGB_8888; 214 case VG_sBGRA_8888_PRE: return VG_sARGB_8888_PRE; 215 case VG_lBGRX_8888: return VG_lXRGB_8888; 216 case VG_lBGRA_8888: return VG_lARGB_8888; 217 case VG_lBGRA_8888_PRE: return VG_lARGB_8888_PRE; 218 case VG_sXBGR_8888: return VG_sRGBX_8888; 219 case VG_sABGR_8888: return VG_sRGBA_8888; 220 case VG_sABGR_8888_PRE: return VG_sRGBA_8888_PRE; 221 case VG_lXBGR_8888: return VG_lRGBX_8888; 222 case VG_lABGR_8888: return VG_lRGBA_8888; 223 case VG_lABGR_8888_PRE: return VG_lRGBA_8888_PRE; 224 default: ASSERT(false); 225 return (VGImageFormat) 0; 226 } 227 } 228 #else 229 VGImageFormat VGUtils::endianAwareImageFormat(VGImageFormat bigEndianFormat) 230 { 231 return bigEndianFormat; 232 } 233 #endif 234 235 } -
trunk/WebCore/platform/graphics/openvg/VGUtils.h
r55369 r59619 86 86 }; 87 87 88 class VGUtils { 89 public: 90 static int bytesForImage(VGImageFormat, VGint width, VGint height); 91 static int bytesForImageScanline(VGImageFormat, VGint width); 92 static int imageFormatBitsPerPixel(VGImageFormat); 93 94 /** 95 * Return a flipped VGImageFormat if the platform is little endian 96 * (e.g. VG_ABGR_8888 for a given VG_RGBA_8888), or return the image format 97 * as is if the platform is big endian. 98 * 99 * OpenVG itself is indifferent to endianness, it will always work on a 100 * single machine word with the bytes going from left to right as specified 101 * in the image format, no matter which one of the bytes is most or least 102 * significant. 103 * 104 * However, if you interface with vgImageSubData()/vgGetImageSubData() 105 * using a byte array then you want to make sure the byte order is 106 * appropriate for the given platform (otherwise the byte indexes need 107 * to be swapped depending on endianness). So, use this function when 108 * interfacing with byte arrays, and don't use it otherwise. 109 */ 110 static VGImageFormat endianAwareImageFormat(VGImageFormat bigEndianFormat); 111 }; 112 88 113 } 89 114
Note: See TracChangeset
for help on using the changeset viewer.