📄 pngimagereader.java
字号:
updateImageProgress(passWidth); // Read the filter type byte and a row of data int filter = pixelStream.read(); try { // Swap curr and prior byte[] tmp = prior; prior = curr; curr = tmp; pixelStream.readFully(curr, 0, bytesPerRow); } catch (java.util.zip.ZipException ze) { // TODO - throw a more meaningful exception throw ze; } switch (filter) { case PNG_FILTER_NONE: break; case PNG_FILTER_SUB: decodeSubFilter(curr, 0, bytesPerRow, bytesPerPixel); break; case PNG_FILTER_UP: decodeUpFilter(curr, 0, prior, 0, bytesPerRow); break; case PNG_FILTER_AVERAGE: decodeAverageFilter(curr, 0, prior, 0, bytesPerRow, bytesPerPixel); break; case PNG_FILTER_PAETH: decodePaethFilter(curr, 0, prior, 0, bytesPerRow, bytesPerPixel); break; default: throw new IIOException("Unknown row filter type (= " + filter + ")!"); } // Copy data into passRow byte by byte if (bitDepth < 16) { System.arraycopy(curr, 0, byteData, 0, bytesPerRow); } else { int idx = 0; for (int j = 0; j < eltsPerRow; j++) { shortData[j] = (short)((curr[idx] << 8) | (curr[idx + 1] & 0xff)); idx += 2; } } // True Y position in source int sourceY = srcY*yStep + yStart; if ((sourceY >= sourceRegion.y) && (sourceY < sourceRegion.y + sourceRegion.height) && (((sourceY - sourceRegion.y) % sourceYSubsampling) == 0)) { int dstY = destinationOffset.y + (sourceY - sourceRegion.y)/sourceYSubsampling; if (dstY < dstMinY) { continue; } if (dstY > dstMaxY) { break; } if (useSetRect) { imRas.setRect(updateMinX, dstY, passRow); } else { int newSrcX = srcX; for (int dstX = updateMinX; dstX < updateMinX + updateWidth; dstX += updateXStep) { passRow.getPixel(newSrcX, 0, ps); if (adjustBitDepths) { for (int b = 0; b < numBands; b++) { ps[b] = scale[b][ps[b]]; } } imRas.setPixel(dstX, dstY, ps); newSrcX += srcXStep; } } processImageUpdate(theImage, updateMinX, dstY, updateWidth, 1, updateXStep, updateYStep, destinationBands); // If read has been aborted, just return // processReadAborted will be called later if (abortRequested()) { return; } } } processPassComplete(theImage); } private void decodeImage() throws IOException, IIOException { int width = metadata.IHDR_width; int height = metadata.IHDR_height; this.pixelsDone = 0; this.totalPixels = width*height; clearAbortRequest(); if (metadata.IHDR_interlaceMethod == 0) { decodePass(0, 0, 0, 1, 1, width, height); } else { for (int i = 0; i <= sourceMaxProgressivePass; i++) { int XOffset = adam7XOffset[i]; int YOffset = adam7YOffset[i]; int XSubsampling = adam7XSubsampling[i]; int YSubsampling = adam7YSubsampling[i]; int xbump = adam7XSubsampling[i + 1] - 1; int ybump = adam7YSubsampling[i + 1] - 1; if (i >= sourceMinProgressivePass) { decodePass(i, XOffset, YOffset, XSubsampling, YSubsampling, (width + xbump)/XSubsampling, (height + ybump)/YSubsampling); } else { skipPass((width + xbump)/XSubsampling, (height + ybump)/YSubsampling); } // If read has been aborted, just return // processReadAborted will be called later if (abortRequested()) { return; } } } } private void readImage(ImageReadParam param) throws IIOException { readMetadata(); int width = metadata.IHDR_width; int height = metadata.IHDR_height; // Init default values sourceRegion = getSourceRegion(param, width, height); sourceXSubsampling = 1; sourceYSubsampling = 1; sourceMinProgressivePass = 0; sourceMaxProgressivePass = 6; sourceBands = null; destinationBands = null; destinationOffset = new Point(0, 0); // If an ImageReadParam is available, get values from it if (param != null) { sourceXSubsampling = param.getSourceXSubsampling(); sourceYSubsampling = param.getSourceYSubsampling(); sourceMinProgressivePass = Math.max(param.getSourceMinProgressivePass(), 0); sourceMaxProgressivePass = Math.min(param.getSourceMaxProgressivePass(), 6); sourceBands = param.getSourceBands(); destinationBands = param.getDestinationBands(); destinationOffset = param.getDestinationOffset(); } try { stream.seek(imageStartPosition); Enumeration e = new PNGImageDataEnumeration(stream); InputStream is = new SequenceInputStream(e); is = new InflaterInputStream(is, new Inflater()); is = new BufferedInputStream(is); this.pixelStream = new DataInputStream(is); theImage = getDestination(param, getImageTypes(0), width, height); // At this point the header has been read and we know // how many bands are in the image, so perform checking // of the read param. int colorType = metadata.IHDR_colorType; checkReadParamBandSettings(param, inputBandsForColorType[colorType], theImage.getSampleModel().getNumBands()); processImageStarted(0); decodeImage(); if (abortRequested()) { processReadAborted(); } else { processImageComplete(); } } catch (IOException e) { e.printStackTrace(); throw new IIOException("Error reading PNG image data", e); } } public int getNumImages(boolean allowSearch) throws IIOException { if (stream == null) { throw new IllegalStateException("No input source set!"); } if (seekForwardOnly && allowSearch) { throw new IllegalStateException ("seekForwardOnly and allowSearch can't both be true!"); } return 1; } public int getWidth(int imageIndex) throws IIOException { readHeader(); return metadata.IHDR_width; } public int getHeight(int imageIndex) throws IIOException { readHeader(); return metadata.IHDR_height; } public Iterator getImageTypes(int imageIndex) throws IIOException { if (imageIndex != 0) { throw new IndexOutOfBoundsException("imageIndex != 0!"); } readHeader(); ArrayList l = new ArrayList(1); // List of ImageTypeSpecifiers ColorSpace rgb; ColorSpace gray; int[] bandOffsets; int bitDepth = metadata.IHDR_bitDepth; int colorType = metadata.IHDR_colorType; int dataType; if (bitDepth <= 8) { dataType = DataBuffer.TYPE_BYTE; } else { dataType = DataBuffer.TYPE_USHORT; } switch (colorType) { case PNG_COLOR_GRAY: // Packed grayscale l.add(ImageTypeSpecifier.createGrayscale(bitDepth, dataType, false)); break; case PNG_COLOR_RGB: // Component R, G, B rgb = ColorSpace.getInstance(ColorSpace.CS_sRGB); bandOffsets = new int[3]; bandOffsets[0] = 0; bandOffsets[1] = 1; bandOffsets[2] = 2; l.add(ImageTypeSpecifier.createInterleaved(rgb, bandOffsets, dataType, false, false)); break; case PNG_COLOR_PALETTE: readMetadata(); // Need tRNS chunk // Alpha from tRNS chunk may have fewer entries than // the RGB LUTs from the PLTE chunk; if so, pad with // 255. byte[] alpha = null; if (metadata.tRNS_present && (metadata.tRNS_alpha != null)) { if (metadata.tRNS_alpha.length == metadata.PLTE_red.length) { alpha = metadata.tRNS_alpha; } else { alpha = new byte[metadata.PLTE_red.length]; System.arraycopy(metadata.tRNS_alpha, 0, alpha, 0, metadata.tRNS_alpha.length); Arrays.fill(alpha, metadata.tRNS_alpha.length, metadata.PLTE_red.length, (byte)255); } } l.add(ImageTypeSpecifier.createIndexed(metadata.PLTE_red, metadata.PLTE_green, metadata.PLTE_blue, alpha, bitDepth, DataBuffer.TYPE_BYTE)); break; case PNG_COLOR_GRAY_ALPHA: // Component G, A gray = ColorSpace.getInstance(ColorSpace.CS_GRAY); bandOffsets = new int[2]; bandOffsets[0] = 0; bandOffsets[1] = 1; l.add(ImageTypeSpecifier.createInterleaved(gray, bandOffsets, dataType, true, false)); break; case PNG_COLOR_RGB_ALPHA: // Component R, G, B, A (non-premultiplied) rgb = ColorSpace.getInstance(ColorSpace.CS_sRGB); bandOffsets = new int[4]; bandOffsets[0] = 0; bandOffsets[1] = 1; bandOffsets[2] = 2; bandOffsets[3] = 3; l.add(ImageTypeSpecifier.createInterleaved(rgb, bandOffsets, dataType, true, false)); break; default: break; } return l.iterator(); } public ImageReadParam getDefaultReadParam() { return new ImageReadParam(); } public IIOMetadata getStreamMetadata() throws IIOException { return null; } public IIOMetadata getImageMetadata(int imageIndex) throws IIOException { if (imageIndex != 0) { throw new IndexOutOfBoundsException("imageIndex != 0!"); } readMetadata(); return metadata; } public BufferedImage read(int imageIndex, ImageReadParam param) throws IIOException { if (imageIndex != 0) { throw new IndexOutOfBoundsException("imageIndex != 0!"); } readImage(param); return theImage; } public void reset() { super.reset(); resetStreamSettings(); } private void resetStreamSettings() { gotHeader = false; gotMetadata = false; metadata = null; pixelStream = null; }}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -