HMCL-dev/HMCL · error · PngFeatureException

Interlaced images are not yet supported

Error message

Interlaced images are not yet supported

What it means

This is a capability guard in checkHeaderParameters: the APNG decoder does not implement Adam7 interlacing, so an IHDR declaring a non-zero interlace method cannot be decoded. It fires on valid-per-spec but unsupported images, signalling a deliberate decoder limitation rather than file corruption.

Solutions

  1. Re-save the image as non-interlaced (e.g. ImageMagick: convert in.png -interlace none out.png).
  2. If you control the encoder, write interlaceMethod = 0 in IHDR.
  3. Use a decoder that supports Adam7 interlacing if interlaced input must be accepted.
  4. Catch PngFeatureException to distinguish 'unsupported feature' from 'corrupt file' and report accordingly.

Example fix

// before: assuming all PNGs decode
decode(pngBytes);
// after: check interlace flag
PngHeader h = PngHeader.from(...);
if (h.getInterlaceMethod() != 0) {
    pngBytes = convertToNonInterlaced(pngBytes); // or reject
}
decode(pngBytes);
Defensive patterns

Strategy: fallback

Validate before calling

if (interlaceMethod != 0) { /* convert or reject */ }

Try / catch

try { decode(bytes); } catch (PngFeatureException e) { bytes = deinterlaceWithImageMagick(bytes); decode(bytes); }

Prevention

When it happens

Trigger: Decoding a PNG saved with 'interlaced' (Adam7) option enabled, producing IHDR interlaceMethod = 1.

Common situations: Images exported from legacy tools or photo editors with interlacing enabled for progressive web display.

Understand the failure class

Background: UnsupportedOperationException and "is not supported" errors: when a library deliberately refuses a call — this error's family across 30 libraries.

Related errors


AI-assisted analysis of HMCL-dev/HMCL@24702dc5a0 (2026-09-10). Data as JSON: /api/errors/5aee84cf27e84b68. Report an issue: GitHub.

Appendix: source

Thrown at HMCL/src/main/java/org/jackhuang/hmcl/ui/image/apng/chunks/PngHeader.java:209

            default:
                throw new PngIntegrityException("Invalid bit depth " + bitDepth);
        }

        // thanks to pypng
        if (colourType.isIndexed() && bitDepth > 8) {
            throw new PngIntegrityException(String.format(
                    "Indexed images (colour type %d) cannot have bitdepth > 8 (bit depth %d)." +
                            " See http://www.w3.org/TR/2003/REC-PNG-20031110/#table111 .", colourType.code, bitDepth));
        }

        if (bitDepth < 8 && !colourType.supportsSubByteDepth()) {
            throw new PngIntegrityException(String.format(
                    "Illegal combination of bit depth (%d) and colour type (%d)." +
                            " See http://www.w3.org/TR/2003/REC-PNG-20031110/#table111 .", colourType.code, bitDepth));
        }

        if (interlaceMethod != 0) {
            throw new PngFeatureException("Interlaced images are not yet supported");
        }
    }

    public static PngHeader from(DataInput dis) throws IOException, PngException {
        int width = dis.readInt();
        int height = dis.readInt();
        byte bitDepth = dis.readByte();
        PngColourType colourType = PngColourType.fromByte(dis.readByte());
        byte compressionMethod = dis.readByte();
        byte filterMethod = dis.readByte();
        byte interlaceMethod = dis.readByte();
        checkHeaderParameters(width, height, bitDepth, colourType, compressionMethod, filterMethod, interlaceMethod);
        return new PngHeader(width, height, bitDepth, colourType, compressionMethod, filterMethod, interlaceMethod);
    }
}

View on GitHub (pinned to 24702dc5a0)