Remove alphaRange from avifImage (#926)

The AVIF draft specification disallows limited range alpha and it
will eventually be in the specification once AOM ratifies it [1] [2].

Even though the default value of alphaRange is set to
AVIF_RANGE_FULL, it is possible for applications to override it
and set it to AVIF_RANGE_LIMITED thereby producing AVIF images
that will eventually be invalid.

On the encoder side, this PR prevents such images from being
produced by libavif.

On the decoder side, if we encounter an image with limited range
alpha, we always convert it to full range alpha and the applications
can assume that alpha plane is always in full range (as it will be
required by the spec eventually).

This change breaks the ABI and a note has been added to CHANGELOG.md
in the "Unreleased" section to document that.

[1] https://github.com/AOMediaCodec/av1-avif/pull/101
[2] https://aomediacodec.github.io/av1-avif/#auxiliary-images
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 8f4c822..5a57e49 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -6,6 +6,13 @@
 
 ## [Unreleased]
 
+There is an incompatible ABI change in this release. Members were removed from
+avifImage struct. It is necessary to recompile your code.
+
+### Removed
+* alphaRange field was removed from the avifImage struct. It it presumed that
+  alpha plane is always full range.
+
 ## [0.10.1] - 2022-04-11
 
 ### Changed
diff --git a/apps/shared/avifutil.c b/apps/shared/avifutil.c
index 27611dd..fe49808 100644
--- a/apps/shared/avifutil.c
+++ b/apps/shared/avifutil.c
@@ -53,10 +53,6 @@
         printf(" * Chroma Sam. Pos: %u\n", avif->yuvChromaSamplePosition);
     }
     printf(" * Alpha          : %s\n", alphaPresent ? (avif->alphaPremultiplied ? "Premultiplied" : "Not premultiplied") : "Absent");
-    if (avif->alphaRange == AVIF_RANGE_LIMITED) {
-        printf("                    Limited range\n");
-        printf("                    WARNING: Limited-range alpha is deprecated. Use full-range alpha instead.\n");
-    }
     printf(" * Range          : %s\n", (avif->yuvRange == AVIF_RANGE_FULL) ? "Full" : "Limited");
 
     printf(" * Color Primaries: %u\n", avif->colorPrimaries);
diff --git a/examples/avif_example_decode_file.c b/examples/avif_example_decode_file.c
index 15102df..12b0a7e 100644
--- a/examples/avif_example_decode_file.c
+++ b/examples/avif_example_decode_file.c
@@ -49,7 +49,7 @@
     while (avifDecoderNextImage(decoder) == AVIF_RESULT_OK) {
         // Now available (for this frame):
         // * All decoder->image YUV pixel data (yuvFormat, yuvPlanes, yuvRange, yuvChromaSamplePosition, yuvRowBytes)
-        // * decoder->image alpha data (alphaRange, alphaPlane, alphaRowBytes)
+        // * decoder->image alpha data (alphaPlane, alphaRowBytes)
         // * this frame's sequence timing
 
         avifRGBImageSetDefaults(&rgb, decoder->image);
diff --git a/examples/avif_example_decode_memory.c b/examples/avif_example_decode_memory.c
index f4c62a1..a50d248 100644
--- a/examples/avif_example_decode_memory.c
+++ b/examples/avif_example_decode_memory.c
@@ -71,7 +71,7 @@
     while (avifDecoderNextImage(decoder) == AVIF_RESULT_OK) {
         // Now available (for this frame):
         // * All decoder->image YUV pixel data (yuvFormat, yuvPlanes, yuvRange, yuvChromaSamplePosition, yuvRowBytes)
-        // * decoder->image alpha data (alphaRange, alphaPlane, alphaRowBytes)
+        // * decoder->image alpha data (alphaPlane, alphaRowBytes)
         // * this frame's sequence timing
 
         avifRGBImageSetDefaults(&rgb, decoder->image);
diff --git a/examples/avif_example_encode.c b/examples/avif_example_encode.c
index a355799..e8812fc 100644
--- a/examples/avif_example_encode.c
+++ b/examples/avif_example_encode.c
@@ -34,7 +34,6 @@
     // * avifImageSetMetadataExif()
     // * avifImageSetMetadataXMP()
     // * yuvRange
-    // * alphaRange
     // * alphaPremultiplied
     // * transforms (transformFlags, pasp, clap, irot, imir)
 
diff --git a/include/avif/avif.h b/include/avif/avif.h
index b887eab..c153a12 100644
--- a/include/avif/avif.h
+++ b/include/avif/avif.h
@@ -433,7 +433,6 @@
     uint32_t yuvRowBytes[AVIF_PLANE_COUNT_YUV];
     avifBool imageOwnsYUVPlanes;
 
-    avifRange alphaRange;
     uint8_t * alphaPlane;
     uint32_t alphaRowBytes;
     avifBool imageOwnsAlphaPlane;
diff --git a/include/avif/internal.h b/include/avif/internal.h
index f88e4e3..ace7611 100644
--- a/include/avif/internal.h
+++ b/include/avif/internal.h
@@ -72,14 +72,12 @@
     uint32_t height;
 
     uint32_t srcDepth;
-    avifRange srcRange;
     uint8_t * srcPlane;
     uint32_t srcRowBytes;
     uint32_t srcOffsetBytes;
     uint32_t srcPixelBytes;
 
     uint32_t dstDepth;
-    avifRange dstRange;
     uint8_t * dstPlane;
     uint32_t dstRowBytes;
     uint32_t dstOffsetBytes;
@@ -127,10 +125,8 @@
     float rgbMaxChannelF;
     float biasY;   // minimum Y value
     float biasUV;  // the value of 0.5 for the appropriate bit depth [128, 512, 2048]
-    float biasA;   // minimum A value
     float rangeY;  // difference between max and min Y
     float rangeUV; // difference between max and min UV
-    float rangeA;  // difference between max and min A
 
     avifPixelFormatInfo formatInfo;
 
@@ -253,6 +249,7 @@
                                               struct avifDecoder * decoder,
                                               const avifDecodeSample * sample,
                                               avifBool alpha,
+                                              avifBool * isLimitedRangeAlpha,
                                               avifImage * image);
 // EncodeImage and EncodeFinish are not required to always emit a sample, but when all images are
 // encoded and EncodeFinish is called, the number of samples emitted must match the number of submitted frames.
diff --git a/src/alpha.c b/src/alpha.c
index c687dc9..0df1697 100644
--- a/src/alpha.c
+++ b/src/alpha.c
@@ -6,19 +6,10 @@
 #include <assert.h>
 #include <string.h>
 
-static int calcMaxChannel(uint32_t depth, avifRange range)
-{
-    int maxChannel = (int)((1 << depth) - 1);
-    if (range == AVIF_RANGE_LIMITED) {
-        maxChannel = avifFullToLimitedY(depth, maxChannel);
-    }
-    return maxChannel;
-}
-
 avifBool avifFillAlpha(const avifAlphaParams * const params)
 {
     if (params->dstDepth > 8) {
-        const uint16_t maxChannel = (uint16_t)calcMaxChannel(params->dstDepth, params->dstRange);
+        const uint16_t maxChannel = (uint16_t)((1 << params->dstDepth) - 1);
         for (uint32_t j = 0; j < params->height; ++j) {
             uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
             for (uint32_t i = 0; i < params->width; ++i) {
@@ -27,7 +18,8 @@
             }
         }
     } else {
-        const uint8_t maxChannel = (uint8_t)calcMaxChannel(params->dstDepth, params->dstRange);
+        // In this case, (1 << params->dstDepth) - 1 is always equal to 255.
+        const uint8_t maxChannel = 255;
         for (uint32_t j = 0; j < params->height; ++j) {
             uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
             for (uint32_t i = 0; i < params->width; ++i) {
@@ -39,8 +31,6 @@
     return AVIF_TRUE;
 }
 
-// Note: The [limited -> limited] paths are here for completeness, but in practice those
-//       paths will never be used, as avifRGBImage is always full range.
 avifBool avifReformatAlpha(const avifAlphaParams * const params)
 {
     const int srcMaxChannel = (1 << params->srcDepth) - 1;
@@ -51,330 +41,75 @@
     if (params->srcDepth == params->dstDepth) {
         // no depth rescale
 
-        if ((params->srcRange == AVIF_RANGE_FULL) && (params->dstRange == AVIF_RANGE_FULL)) {
-            // no depth rescale, no range conversion
+        if (params->srcDepth > 8) {
+            // no depth rescale, uint16_t -> uint16_t
 
-            if (params->srcDepth > 8) {
-                // no depth rescale, no range conversion, uint16_t -> uint16_t
-
-                for (uint32_t j = 0; j < params->height; ++j) {
-                    uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                    uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                    for (uint32_t i = 0; i < params->width; ++i) {
-                        *((uint16_t *)&dstRow[i * params->dstPixelBytes]) = *((uint16_t *)&srcRow[i * params->srcPixelBytes]);
-                    }
-                }
-            } else {
-                // no depth rescale, no range conversion, uint8_t -> uint8_t
-
-                for (uint32_t j = 0; j < params->height; ++j) {
-                    uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                    uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                    for (uint32_t i = 0; i < params->width; ++i) {
-                        dstRow[i * params->dstPixelBytes] = srcRow[i * params->srcPixelBytes];
-                    }
+            for (uint32_t j = 0; j < params->height; ++j) {
+                uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
+                uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
+                for (uint32_t i = 0; i < params->width; ++i) {
+                    *((uint16_t *)&dstRow[i * params->dstPixelBytes]) = *((uint16_t *)&srcRow[i * params->srcPixelBytes]);
                 }
             }
-        } else if ((params->srcRange == AVIF_RANGE_LIMITED) && (params->dstRange == AVIF_RANGE_FULL)) {
-            // limited -> full
+        } else {
+            // no depth rescale, uint8_t -> uint8_t
 
-            if (params->srcDepth > 8) {
-                // no depth rescale, limited -> full, uint16_t -> uint16_t
-
-                for (uint32_t j = 0; j < params->height; ++j) {
-                    uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                    uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                    for (uint32_t i = 0; i < params->width; ++i) {
-                        int srcAlpha = *((uint16_t *)&srcRow[i * params->srcPixelBytes]);
-                        int dstAlpha = avifLimitedToFullY(params->srcDepth, srcAlpha);
-                        *((uint16_t *)&dstRow[i * params->dstPixelBytes]) = (uint16_t)dstAlpha;
-                    }
-                }
-            } else {
-                // no depth rescale, limited -> full, uint8_t -> uint8_t
-
-                for (uint32_t j = 0; j < params->height; ++j) {
-                    uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                    uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                    for (uint32_t i = 0; i < params->width; ++i) {
-                        int srcAlpha = srcRow[i * params->srcPixelBytes];
-                        int dstAlpha = avifLimitedToFullY(params->srcDepth, srcAlpha);
-                        dstRow[i * params->dstPixelBytes] = (uint8_t)dstAlpha;
-                    }
-                }
-            }
-        } else if ((params->srcRange == AVIF_RANGE_FULL) && (params->dstRange == AVIF_RANGE_LIMITED)) {
-            // full -> limited
-
-            if (params->srcDepth > 8) {
-                // no depth rescale, full -> limited, uint16_t -> uint16_t
-
-                for (uint32_t j = 0; j < params->height; ++j) {
-                    uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                    uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                    for (uint32_t i = 0; i < params->width; ++i) {
-                        int srcAlpha = *((uint16_t *)&srcRow[i * params->srcPixelBytes]);
-                        int dstAlpha = avifFullToLimitedY(params->dstDepth, srcAlpha);
-                        *((uint16_t *)&dstRow[i * params->dstPixelBytes]) = (uint16_t)dstAlpha;
-                    }
-                }
-            } else {
-                // no depth rescale, full -> limited, uint8_t -> uint8_t
-
-                for (uint32_t j = 0; j < params->height; ++j) {
-                    uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                    uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                    for (uint32_t i = 0; i < params->width; ++i) {
-                        int srcAlpha = srcRow[i * params->srcPixelBytes];
-                        int dstAlpha = avifFullToLimitedY(params->dstDepth, srcAlpha);
-                        dstRow[i * params->dstPixelBytes] = (uint8_t)dstAlpha;
-                    }
-                }
-            }
-        } else if ((params->srcRange == AVIF_RANGE_LIMITED) && (params->dstRange == AVIF_RANGE_LIMITED)) {
-            // limited -> limited
-
-            if (params->srcDepth > 8) {
-                // no depth rescale, limited -> limited, uint16_t -> uint16_t
-
-                for (uint32_t j = 0; j < params->height; ++j) {
-                    uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                    uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                    for (uint32_t i = 0; i < params->width; ++i) {
-                        *((uint16_t *)&dstRow[i * params->dstPixelBytes]) = *((uint16_t *)&srcRow[i * params->srcPixelBytes]);
-                    }
-                }
-            } else {
-                // no depth rescale, limited -> limited, uint8_t -> uint8_t
-
-                for (uint32_t j = 0; j < params->height; ++j) {
-                    uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                    uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                    for (uint32_t i = 0; i < params->width; ++i) {
-                        dstRow[i * params->dstPixelBytes] = srcRow[i * params->srcPixelBytes];
-                    }
+            for (uint32_t j = 0; j < params->height; ++j) {
+                uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
+                uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
+                for (uint32_t i = 0; i < params->width; ++i) {
+                    dstRow[i * params->dstPixelBytes] = srcRow[i * params->srcPixelBytes];
                 }
             }
         }
-
     } else {
         // depth rescale
 
-        if ((params->srcRange == AVIF_RANGE_FULL) && (params->dstRange == AVIF_RANGE_FULL)) {
-            // depth rescale, no range conversion
-
-            if (params->srcDepth > 8) {
-                if (params->dstDepth > 8) {
-                    // depth rescale, no range conversion, uint16_t -> uint16_t
-
-                    for (uint32_t j = 0; j < params->height; ++j) {
-                        uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                        uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                        for (uint32_t i = 0; i < params->width; ++i) {
-                            int srcAlpha = *((uint16_t *)&srcRow[i * params->srcPixelBytes]);
-                            float alphaF = (float)srcAlpha / srcMaxChannelF;
-                            int dstAlpha = (int)(0.5f + (alphaF * dstMaxChannelF));
-                            dstAlpha = AVIF_CLAMP(dstAlpha, 0, dstMaxChannel);
-                            *((uint16_t *)&dstRow[i * params->dstPixelBytes]) = (uint16_t)dstAlpha;
-                        }
-                    }
-                } else {
-                    // depth rescale, no range conversion, uint16_t -> uint8_t
-
-                    for (uint32_t j = 0; j < params->height; ++j) {
-                        uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                        uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                        for (uint32_t i = 0; i < params->width; ++i) {
-                            int srcAlpha = *((uint16_t *)&srcRow[i * params->srcPixelBytes]);
-                            float alphaF = (float)srcAlpha / srcMaxChannelF;
-                            int dstAlpha = (int)(0.5f + (alphaF * dstMaxChannelF));
-                            dstAlpha = AVIF_CLAMP(dstAlpha, 0, dstMaxChannel);
-                            dstRow[i * params->dstPixelBytes] = (uint8_t)dstAlpha;
-                        }
-                    }
-                }
-            } else {
-                // depth rescale, no range conversion, uint8_t -> uint16_t
+        if (params->srcDepth > 8) {
+            if (params->dstDepth > 8) {
+                // depth rescale, uint16_t -> uint16_t
 
                 for (uint32_t j = 0; j < params->height; ++j) {
                     uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
                     uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
                     for (uint32_t i = 0; i < params->width; ++i) {
-                        int srcAlpha = srcRow[i * params->srcPixelBytes];
+                        int srcAlpha = *((uint16_t *)&srcRow[i * params->srcPixelBytes]);
                         float alphaF = (float)srcAlpha / srcMaxChannelF;
                         int dstAlpha = (int)(0.5f + (alphaF * dstMaxChannelF));
                         dstAlpha = AVIF_CLAMP(dstAlpha, 0, dstMaxChannel);
                         *((uint16_t *)&dstRow[i * params->dstPixelBytes]) = (uint16_t)dstAlpha;
                     }
                 }
+            } else {
+                // depth rescale, uint16_t -> uint8_t
 
-                // If (srcDepth == 8), dstDepth must be >8 otherwise we'd be in the (params->srcDepth == params->dstDepth) block above.
-                // assert(params->dstDepth > 8);
+                for (uint32_t j = 0; j < params->height; ++j) {
+                    uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
+                    uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
+                    for (uint32_t i = 0; i < params->width; ++i) {
+                        int srcAlpha = *((uint16_t *)&srcRow[i * params->srcPixelBytes]);
+                        float alphaF = (float)srcAlpha / srcMaxChannelF;
+                        int dstAlpha = (int)(0.5f + (alphaF * dstMaxChannelF));
+                        dstAlpha = AVIF_CLAMP(dstAlpha, 0, dstMaxChannel);
+                        dstRow[i * params->dstPixelBytes] = (uint8_t)dstAlpha;
+                    }
+                }
             }
-        } else if ((params->srcRange == AVIF_RANGE_LIMITED) && (params->dstRange == AVIF_RANGE_FULL)) {
-            // limited -> full
+        } else {
+            // If (srcDepth == 8), dstDepth must be >8 otherwise we'd be in the (params->srcDepth == params->dstDepth) block above.
+            assert(params->dstDepth > 8);
 
-            if (params->srcDepth > 8) {
-                if (params->dstDepth > 8) {
-                    // depth rescale, limited -> full, uint16_t -> uint16_t
-
-                    for (uint32_t j = 0; j < params->height; ++j) {
-                        uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                        uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                        for (uint32_t i = 0; i < params->width; ++i) {
-                            int srcAlpha = *((uint16_t *)&srcRow[i * params->srcPixelBytes]);
-                            srcAlpha = avifLimitedToFullY(params->srcDepth, srcAlpha);
-                            float alphaF = (float)srcAlpha / srcMaxChannelF;
-                            int dstAlpha = (int)(0.5f + (alphaF * dstMaxChannelF));
-                            dstAlpha = AVIF_CLAMP(dstAlpha, 0, dstMaxChannel);
-                            *((uint16_t *)&dstRow[i * params->dstPixelBytes]) = (uint16_t)dstAlpha;
-                        }
-                    }
-                } else {
-                    // depth rescale, limited -> full, uint16_t -> uint8_t
-
-                    for (uint32_t j = 0; j < params->height; ++j) {
-                        uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                        uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                        for (uint32_t i = 0; i < params->width; ++i) {
-                            int srcAlpha = *((uint16_t *)&srcRow[i * params->srcPixelBytes]);
-                            srcAlpha = avifLimitedToFullY(params->srcDepth, srcAlpha);
-                            float alphaF = (float)srcAlpha / srcMaxChannelF;
-                            int dstAlpha = (int)(0.5f + (alphaF * dstMaxChannelF));
-                            dstAlpha = AVIF_CLAMP(dstAlpha, 0, dstMaxChannel);
-                            dstRow[i * params->dstPixelBytes] = (uint8_t)dstAlpha;
-                        }
-                    }
+            // depth rescale, uint8_t -> uint16_t
+            for (uint32_t j = 0; j < params->height; ++j) {
+                uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
+                uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
+                for (uint32_t i = 0; i < params->width; ++i) {
+                    int srcAlpha = srcRow[i * params->srcPixelBytes];
+                    float alphaF = (float)srcAlpha / srcMaxChannelF;
+                    int dstAlpha = (int)(0.5f + (alphaF * dstMaxChannelF));
+                    dstAlpha = AVIF_CLAMP(dstAlpha, 0, dstMaxChannel);
+                    *((uint16_t *)&dstRow[i * params->dstPixelBytes]) = (uint16_t)dstAlpha;
                 }
-            } else {
-                // depth rescale, limited -> full, uint8_t -> uint16_t
-
-                for (uint32_t j = 0; j < params->height; ++j) {
-                    uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                    uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                    for (uint32_t i = 0; i < params->width; ++i) {
-                        int srcAlpha = srcRow[i * params->srcPixelBytes];
-                        srcAlpha = avifLimitedToFullY(params->srcDepth, srcAlpha);
-                        float alphaF = (float)srcAlpha / srcMaxChannelF;
-                        int dstAlpha = (int)(0.5f + (alphaF * dstMaxChannelF));
-                        dstAlpha = AVIF_CLAMP(dstAlpha, 0, dstMaxChannel);
-                        *((uint16_t *)&dstRow[i * params->dstPixelBytes]) = (uint16_t)dstAlpha;
-                    }
-                }
-
-                // If (srcDepth == 8), dstDepth must be >8 otherwise we'd be in the (params->srcDepth == params->dstDepth) block above.
-                // assert(params->dstDepth > 8);
-            }
-        } else if ((params->srcRange == AVIF_RANGE_FULL) && (params->dstRange == AVIF_RANGE_LIMITED)) {
-            // full -> limited
-
-            if (params->srcDepth > 8) {
-                if (params->dstDepth > 8) {
-                    // depth rescale, full -> limited, uint16_t -> uint16_t
-
-                    for (uint32_t j = 0; j < params->height; ++j) {
-                        uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                        uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                        for (uint32_t i = 0; i < params->width; ++i) {
-                            int srcAlpha = *((uint16_t *)&srcRow[i * params->srcPixelBytes]);
-                            float alphaF = (float)srcAlpha / srcMaxChannelF;
-                            int dstAlpha = (int)(0.5f + (alphaF * dstMaxChannelF));
-                            dstAlpha = AVIF_CLAMP(dstAlpha, 0, dstMaxChannel);
-                            dstAlpha = avifFullToLimitedY(params->dstDepth, dstAlpha);
-                            *((uint16_t *)&dstRow[i * params->dstPixelBytes]) = (uint16_t)dstAlpha;
-                        }
-                    }
-                } else {
-                    // depth rescale, full -> limited, uint16_t -> uint8_t
-
-                    for (uint32_t j = 0; j < params->height; ++j) {
-                        uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                        uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                        for (uint32_t i = 0; i < params->width; ++i) {
-                            int srcAlpha = *((uint16_t *)&srcRow[i * params->srcPixelBytes]);
-                            float alphaF = (float)srcAlpha / srcMaxChannelF;
-                            int dstAlpha = (int)(0.5f + (alphaF * dstMaxChannelF));
-                            dstAlpha = AVIF_CLAMP(dstAlpha, 0, dstMaxChannel);
-                            dstAlpha = avifFullToLimitedY(params->dstDepth, dstAlpha);
-                            dstRow[i * params->dstPixelBytes] = (uint8_t)dstAlpha;
-                        }
-                    }
-                }
-            } else {
-                // depth rescale, full -> limited, uint8_t -> uint16_t
-
-                for (uint32_t j = 0; j < params->height; ++j) {
-                    uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                    uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                    for (uint32_t i = 0; i < params->width; ++i) {
-                        int srcAlpha = srcRow[i * params->srcPixelBytes];
-                        float alphaF = (float)srcAlpha / srcMaxChannelF;
-                        int dstAlpha = (int)(0.5f + (alphaF * dstMaxChannelF));
-                        dstAlpha = AVIF_CLAMP(dstAlpha, 0, dstMaxChannel);
-                        dstAlpha = avifFullToLimitedY(params->dstDepth, dstAlpha);
-                        *((uint16_t *)&dstRow[i * params->dstPixelBytes]) = (uint16_t)dstAlpha;
-                    }
-                }
-
-                // If (srcDepth == 8), dstDepth must be >8 otherwise we'd be in the (params->srcDepth == params->dstDepth) block above.
-                // assert(params->dstDepth > 8);
-            }
-        } else if ((params->srcRange == AVIF_RANGE_LIMITED) && (params->dstRange == AVIF_RANGE_LIMITED)) {
-            // limited -> limited
-
-            if (params->srcDepth > 8) {
-                if (params->dstDepth > 8) {
-                    // depth rescale, limited -> limited, uint16_t -> uint16_t
-
-                    for (uint32_t j = 0; j < params->height; ++j) {
-                        uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                        uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                        for (uint32_t i = 0; i < params->width; ++i) {
-                            int srcAlpha = *((uint16_t *)&srcRow[i * params->srcPixelBytes]);
-                            srcAlpha = avifLimitedToFullY(params->srcDepth, srcAlpha);
-                            float alphaF = (float)srcAlpha / srcMaxChannelF;
-                            int dstAlpha = (int)(0.5f + (alphaF * dstMaxChannelF));
-                            dstAlpha = AVIF_CLAMP(dstAlpha, 0, dstMaxChannel);
-                            dstAlpha = avifFullToLimitedY(params->dstDepth, dstAlpha);
-                            *((uint16_t *)&dstRow[i * params->dstPixelBytes]) = (uint16_t)dstAlpha;
-                        }
-                    }
-                } else {
-                    // depth rescale, limited -> limited, uint16_t -> uint8_t
-
-                    for (uint32_t j = 0; j < params->height; ++j) {
-                        uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                        uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                        for (uint32_t i = 0; i < params->width; ++i) {
-                            int srcAlpha = *((uint16_t *)&srcRow[i * params->srcPixelBytes]);
-                            srcAlpha = avifLimitedToFullY(params->srcDepth, srcAlpha);
-                            float alphaF = (float)srcAlpha / srcMaxChannelF;
-                            int dstAlpha = (int)(0.5f + (alphaF * dstMaxChannelF));
-                            dstAlpha = AVIF_CLAMP(dstAlpha, 0, dstMaxChannel);
-                            dstAlpha = avifFullToLimitedY(params->dstDepth, dstAlpha);
-                            dstRow[i * params->dstPixelBytes] = (uint8_t)dstAlpha;
-                        }
-                    }
-                }
-            } else {
-                // depth rescale, limited -> limited, uint8_t -> uint16_t
-
-                for (uint32_t j = 0; j < params->height; ++j) {
-                    uint8_t * srcRow = &params->srcPlane[params->srcOffsetBytes + (j * params->srcRowBytes)];
-                    uint8_t * dstRow = &params->dstPlane[params->dstOffsetBytes + (j * params->dstRowBytes)];
-                    for (uint32_t i = 0; i < params->width; ++i) {
-                        int srcAlpha = srcRow[i * params->srcPixelBytes];
-                        srcAlpha = avifLimitedToFullY(params->srcDepth, srcAlpha);
-                        float alphaF = (float)srcAlpha / srcMaxChannelF;
-                        int dstAlpha = (int)(0.5f + (alphaF * dstMaxChannelF));
-                        dstAlpha = AVIF_CLAMP(dstAlpha, 0, dstMaxChannel);
-                        dstAlpha = avifFullToLimitedY(params->dstDepth, dstAlpha);
-                        *((uint16_t *)&dstRow[i * params->dstPixelBytes]) = (uint16_t)dstAlpha;
-                    }
-                }
-
-                // If (srcDepth == 8), dstDepth must be >8 otherwise we'd be in the (params->srcDepth == params->dstDepth) block above.
-                // assert(params->dstDepth > 8);
             }
         }
     }
diff --git a/src/avif.c b/src/avif.c
index 24e4c5a..739066c 100644
--- a/src/avif.c
+++ b/src/avif.c
@@ -120,7 +120,6 @@
 {
     memset(image, 0, sizeof(avifImage));
     image->yuvRange = AVIF_RANGE_FULL;
-    image->alphaRange = AVIF_RANGE_FULL;
     image->colorPrimaries = AVIF_COLOR_PRIMARIES_UNSPECIFIED;
     image->transferCharacteristics = AVIF_TRANSFER_CHARACTERISTICS_UNSPECIFIED;
     image->matrixCoefficients = AVIF_MATRIX_COEFFICIENTS_UNSPECIFIED;
@@ -151,7 +150,6 @@
     dstImage->yuvFormat = srcImage->yuvFormat;
     dstImage->yuvRange = srcImage->yuvRange;
     dstImage->yuvChromaSamplePosition = srcImage->yuvChromaSamplePosition;
-    dstImage->alphaRange = srcImage->alphaRange;
     dstImage->alphaPremultiplied = srcImage->alphaPremultiplied;
 
     dstImage->colorPrimaries = srcImage->colorPrimaries;
diff --git a/src/codec_aom.c b/src/codec_aom.c
index 972a2ae..4a5a7b1 100644
--- a/src/codec_aom.c
+++ b/src/codec_aom.c
@@ -95,6 +95,7 @@
                                      struct avifDecoder * decoder,
                                      const avifDecodeSample * sample,
                                      avifBool alpha,
+                                     avifBool * isLimitedRangeAlpha,
                                      avifImage * image)
 {
     if (!codec->internal->decoderInitialized) {
@@ -239,7 +240,7 @@
         avifImageFreePlanes(image, AVIF_PLANES_A);
         image->alphaPlane = codec->internal->image->planes[0];
         image->alphaRowBytes = codec->internal->image->stride[0];
-        image->alphaRange = (codec->internal->image->range == AOM_CR_STUDIO_RANGE) ? AVIF_RANGE_LIMITED : AVIF_RANGE_FULL;
+        *isLimitedRangeAlpha = (codec->internal->image->range == AOM_CR_STUDIO_RANGE);
         image->imageOwnsAlphaPlane = AVIF_FALSE;
     }
 
@@ -782,7 +783,7 @@
     avifBool monochromeRequested = AVIF_FALSE;
 
     if (alpha) {
-        aomImage.range = (image->alphaRange == AVIF_RANGE_FULL) ? AOM_CR_FULL_RANGE : AOM_CR_STUDIO_RANGE;
+        aomImage.range = AOM_CR_FULL_RANGE;
         aom_codec_control(&codec->internal->encoder, AV1E_SET_COLOR_RANGE, aomImage.range);
         monochromeRequested = AVIF_TRUE;
         if (aomImageAllocated) {
diff --git a/src/codec_dav1d.c b/src/codec_dav1d.c
index bdadfbf..680c10f 100644
--- a/src/codec_dav1d.c
+++ b/src/codec_dav1d.c
@@ -53,6 +53,7 @@
                                        struct avifDecoder * decoder,
                                        const avifDecodeSample * sample,
                                        avifBool alpha,
+                                       avifBool * isLimitedRangeAlpha,
                                        avifImage * image)
 {
     if (codec->internal->dav1dContext == NULL) {
@@ -204,7 +205,7 @@
         avifImageFreePlanes(image, AVIF_PLANES_A);
         image->alphaPlane = dav1dImage->data[0];
         image->alphaRowBytes = (uint32_t)dav1dImage->stride[0];
-        image->alphaRange = codec->internal->colorRange;
+        *isLimitedRangeAlpha = (codec->internal->colorRange == AVIF_RANGE_LIMITED);
         image->imageOwnsAlphaPlane = AVIF_FALSE;
     }
     return AVIF_TRUE;
diff --git a/src/codec_libgav1.c b/src/codec_libgav1.c
index de5fa15..537f020 100644
--- a/src/codec_libgav1.c
+++ b/src/codec_libgav1.c
@@ -27,6 +27,7 @@
                                       struct avifDecoder * decoder,
                                       const avifDecodeSample * sample,
                                       avifBool alpha,
+                                      avifBool * isLimitedRangeAlpha,
                                       avifImage * image)
 {
     if (codec->internal->gav1Decoder == NULL) {
@@ -144,7 +145,7 @@
         avifImageFreePlanes(image, AVIF_PLANES_A);
         image->alphaPlane = gav1Image->plane[0];
         image->alphaRowBytes = gav1Image->stride[0];
-        image->alphaRange = codec->internal->colorRange;
+        *isLimitedRangeAlpha = (codec->internal->colorRange == AVIF_RANGE_LIMITED);
         image->imageOwnsAlphaPlane = AVIF_FALSE;
     }
 
diff --git a/src/codec_rav1e.c b/src/codec_rav1e.c
index 2ae3832..438ff5e 100644
--- a/src/codec_rav1e.c
+++ b/src/codec_rav1e.c
@@ -68,7 +68,7 @@
         const avifBool supports400 = rav1eSupports400();
         RaPixelRange rav1eRange;
         if (alpha) {
-            rav1eRange = (image->alphaRange == AVIF_RANGE_FULL) ? RA_PIXEL_RANGE_FULL : RA_PIXEL_RANGE_LIMITED;
+            rav1eRange = RA_PIXEL_RANGE_FULL;
             codec->internal->chromaSampling = supports400 ? RA_CHROMA_SAMPLING_CS400 : RA_CHROMA_SAMPLING_CS420;
             codec->internal->yShift = 1;
         } else {
diff --git a/src/codec_svt.c b/src/codec_svt.c
index 5bc80cd..1ddf83e 100644
--- a/src/codec_svt.c
+++ b/src/codec_svt.c
@@ -57,7 +57,7 @@
     int y_shift = 0;
     // EbColorRange svt_range;
     if (alpha) {
-        // svt_range = (image->alphaRange == AVIF_RANGE_FULL) ? EB_CR_FULL_RANGE : EB_CR_STUDIO_RANGE;
+        // svt_range = EB_CR_FULL_RANGE;
         y_shift = 1;
     } else {
         // svt_range = (image->yuvRange == AVIF_RANGE_FULL) ? EB_CR_FULL_RANGE : EB_CR_STUDIO_RANGE;
diff --git a/src/read.c b/src/read.c
index 8d39b07..70ed7fc 100644
--- a/src/read.c
+++ b/src/read.c
@@ -1297,8 +1297,7 @@
             (tile->image->yuvRange != firstTile->image->yuvRange) || (uvPresent != firstTileUVPresent) ||
             (tile->image->colorPrimaries != firstTile->image->colorPrimaries) ||
             (tile->image->transferCharacteristics != firstTile->image->transferCharacteristics) ||
-            (tile->image->matrixCoefficients != firstTile->image->matrixCoefficients) ||
-            (tile->image->alphaRange != firstTile->image->alphaRange)) {
+            (tile->image->matrixCoefficients != firstTile->image->matrixCoefficients)) {
             avifDiagnosticsPrintf(data->diag, "Grid image contains mismatched tiles");
             return AVIF_FALSE;
         }
@@ -1358,9 +1357,6 @@
             dstImage->matrixCoefficients = firstTile->image->matrixCoefficients;
         }
     }
-    if (alpha) {
-        dstImage->alphaRange = firstTile->image->alphaRange;
-    }
 
     avifImageAllocatePlanes(dstImage, alpha ? AVIF_PLANES_A : AVIF_PLANES_YUV);
 
@@ -3730,6 +3726,45 @@
     return AVIF_RESULT_OK;
 }
 
+static avifResult avifImageLimitedToFullAlpha(avifImage * image)
+{
+    if (image->imageOwnsAlphaPlane) {
+        return AVIF_RESULT_NOT_IMPLEMENTED;
+    }
+
+    uint8_t * alphaPlane = image->alphaPlane;
+    const uint32_t alphaRowBytes = image->alphaRowBytes;
+
+    // We cannot do the range conversion in place since it will modify the
+    // codec's internal frame buffers. Allocate memory for the conversion.
+    image->alphaPlane = NULL;
+    image->alphaRowBytes = 0;
+    avifImageAllocatePlanes(image, AVIF_PLANES_A);
+
+    if (image->depth > 8) {
+        for (uint32_t j = 0; j < image->height; ++j) {
+            uint8_t * srcRow = &alphaPlane[j * alphaRowBytes];
+            uint8_t * dstRow = &image->alphaPlane[j * image->alphaRowBytes];
+            for (uint32_t i = 0; i < image->width; ++i) {
+                int srcAlpha = *((uint16_t *)&srcRow[i * 2]);
+                int dstAlpha = avifLimitedToFullY(image->depth, srcAlpha);
+                *((uint16_t *)&dstRow[i * 2]) = (uint16_t)dstAlpha;
+            }
+        }
+    } else {
+        for (uint32_t j = 0; j < image->height; ++j) {
+            uint8_t * srcRow = &alphaPlane[j * alphaRowBytes];
+            uint8_t * dstRow = &image->alphaPlane[j * image->alphaRowBytes];
+            for (uint32_t i = 0; i < image->width; ++i) {
+                int srcAlpha = srcRow[i];
+                int dstAlpha = avifLimitedToFullY(image->depth, srcAlpha);
+                dstRow[i] = (uint8_t)dstAlpha;
+            }
+        }
+    }
+    return AVIF_RESULT_OK;
+}
+
 static avifResult avifDecoderDecodeTiles(avifDecoder * decoder,
                                          uint32_t nextImageIndex,
                                          unsigned int firstTileIndex,
@@ -3747,11 +3782,24 @@
             return AVIF_RESULT_OK;
         }
 
-        if (!tile->codec->getNextImage(tile->codec, decoder, sample, tile->input->alpha, tile->image)) {
+        avifBool isLimitedRangeAlpha = AVIF_FALSE;
+        if (!tile->codec->getNextImage(tile->codec, decoder, sample, tile->input->alpha, &isLimitedRangeAlpha, tile->image)) {
             avifDiagnosticsPrintf(&decoder->diag, "tile->codec->getNextImage() failed");
             return tile->input->alpha ? AVIF_RESULT_DECODE_ALPHA_FAILED : AVIF_RESULT_DECODE_COLOR_FAILED;
         }
 
+        // Alpha plane with limited range is not allowed by the latest revision
+        // of the specification. However, it was allowed in version 1.0.0 of the
+        // specification. To allow such files, simply convert the alpha plane to
+        // full range.
+        if (tile->input->alpha && isLimitedRangeAlpha) {
+            avifResult result = avifImageLimitedToFullAlpha(tile->image);
+            if (result != AVIF_RESULT_OK) {
+                avifDiagnosticsPrintf(&decoder->diag, "avifImageLimitedToFullAlpha failed");
+                return result;
+            }
+        }
+
         // Scale the decoded image so that it corresponds to this tile's output dimensions
         if ((tile->width != tile->image->width) || (tile->height != tile->image->height)) {
             if (!avifImageScale(tile->image, tile->width, tile->height, decoder->imageSizeLimit, &decoder->diag)) {
@@ -3889,7 +3937,6 @@
             }
 
             avifImageStealPlanes(decoder->image, srcAlpha, AVIF_PLANES_A);
-            decoder->image->alphaRange = srcAlpha->alphaRange;
         }
     }
 
diff --git a/src/reformat.c b/src/reformat.c
index ea48196..7d7c13f 100644
--- a/src/reformat.c
+++ b/src/reformat.c
@@ -117,10 +117,8 @@
     state->rgbMaxChannelF = (float)state->rgbMaxChannel;
     state->biasY = (state->yuvRange == AVIF_RANGE_LIMITED) ? (float)(16 << (state->yuvDepth - 8)) : 0.0f;
     state->biasUV = (float)(1 << (state->yuvDepth - 1));
-    state->biasA = (image->alphaRange == AVIF_RANGE_LIMITED) ? (float)(16 << (state->yuvDepth - 8)) : 0.0f;
     state->rangeY = (float)((state->yuvRange == AVIF_RANGE_LIMITED) ? (219 << (state->yuvDepth - 8)) : state->yuvMaxChannel);
     state->rangeUV = (float)((state->yuvRange == AVIF_RANGE_LIMITED) ? (224 << (state->yuvDepth - 8)) : state->yuvMaxChannel);
-    state->rangeA = (float)((image->alphaRange == AVIF_RANGE_LIMITED) ? (219 << (state->yuvDepth - 8)) : state->yuvMaxChannel);
 
     uint32_t cpCount = 1 << image->depth;
     if (state->mode == AVIF_REFORMAT_MODE_IDENTITY) {
@@ -394,7 +392,6 @@
         params.width = image->width;
         params.height = image->height;
         params.dstDepth = image->depth;
-        params.dstRange = image->alphaRange;
         params.dstPlane = image->alphaPlane;
         params.dstRowBytes = image->alphaRowBytes;
         params.dstOffsetBytes = 0;
@@ -402,7 +399,6 @@
 
         if (avifRGBFormatHasAlpha(rgb->format) && !rgb->ignoreAlpha) {
             params.srcDepth = rgb->depth;
-            params.srcRange = AVIF_RANGE_FULL;
             params.srcPlane = rgb->pixels;
             params.srcRowBytes = rgb->rowBytes;
             params.srcOffsetBytes = state.rgbOffsetBytesA;
@@ -645,7 +641,7 @@
                 } else {
                     unormA = AVIF_MIN(ptrA16[i], yuvMaxChannel);
                 }
-                const float A = (unormA - state->biasA) / state->rangeA;
+                const float A = unormA / ((float)state->yuvMaxChannel);
                 const float Ac = AVIF_CLAMP(A, 0.0f, 1.0f);
 
                 if (state->toRGBAlphaMode == AVIF_ALPHA_MULTIPLY_MODE_MULTIPLY) {
@@ -1140,7 +1136,6 @@
         params.width = rgb->width;
         params.height = rgb->height;
         params.dstDepth = rgb->depth;
-        params.dstRange = AVIF_RANGE_FULL;
         params.dstPlane = rgb->pixels;
         params.dstRowBytes = rgb->rowBytes;
         params.dstOffsetBytes = state.rgbOffsetBytesA;
@@ -1148,7 +1143,6 @@
 
         if (image->alphaPlane && image->alphaRowBytes) {
             params.srcDepth = image->depth;
-            params.srcRange = image->alphaRange;
             params.srcPlane = image->alphaPlane;
             params.srcRowBytes = image->alphaRowBytes;
             params.srcOffsetBytes = 0;
diff --git a/src/write.c b/src/write.c
index ad05931..52b16a7 100644
--- a/src/write.c
+++ b/src/write.c
@@ -589,7 +589,7 @@
             (cellImage->depth != firstCell->depth) || (cellImage->yuvFormat != firstCell->yuvFormat) ||
             (cellImage->yuvRange != firstCell->yuvRange) || (cellImage->colorPrimaries != firstCell->colorPrimaries) ||
             (cellImage->transferCharacteristics != firstCell->transferCharacteristics) ||
-            (cellImage->matrixCoefficients != firstCell->matrixCoefficients) || (cellImage->alphaRange != firstCell->alphaRange) ||
+            (cellImage->matrixCoefficients != firstCell->matrixCoefficients) ||
             (!!cellImage->alphaPlane != !!firstCell->alphaPlane) || (cellImage->alphaPremultiplied != firstCell->alphaPremultiplied)) {
             return AVIF_RESULT_INVALID_IMAGE_GRID;
         }
diff --git a/tests/avifincrtest.c b/tests/avifincrtest.c
index 821ba21..b2162d5 100644
--- a/tests/avifincrtest.c
+++ b/tests/avifincrtest.c
@@ -75,7 +75,7 @@
     }
 
     if (image1->alphaPlane) {
-        if (!image2->alphaPlane || (image1->alphaRange != image2->alphaRange) ||
+        if (!image2->alphaPlane ||
             (image1->alphaPremultiplied != image2->alphaPremultiplied)) {
             printf("ERROR: input mismatch\n");
             return AVIF_FALSE;
@@ -301,7 +301,6 @@
         }
         subImage->alphaPlane = image->yuvPlanes[AVIF_CHAN_Y];
         subImage->alphaRowBytes = image->yuvRowBytes[AVIF_CHAN_Y];
-        subImage->alphaRange = AVIF_RANGE_FULL;
         subImage->alphaPremultiplied = AVIF_FALSE;
         subImage->imageOwnsAlphaPlane = AVIF_FALSE;
     }
diff --git a/tests/avify4mtest.c b/tests/avify4mtest.c
index 2f1194b..8be2799 100644
--- a/tests/avify4mtest.c
+++ b/tests/avify4mtest.c
@@ -46,7 +46,7 @@
     }
 
     if (image1->alphaPlane != NULL || image2->alphaPlane != NULL) {
-        if (image1->alphaPlane == NULL || image2->alphaPlane == NULL || image1->alphaRange != image2->alphaRange ||
+        if (image1->alphaPlane == NULL || image2->alphaPlane == NULL ||
             image1->alphaPremultiplied != image2->alphaPremultiplied) {
             printf("ERROR: input mismatch\n");
             return AVIF_FALSE;
@@ -94,7 +94,6 @@
         }
     }
     if (image->alphaPlane != NULL) {
-        assert(image->alphaRange == AVIF_RANGE_FULL);
         const uint16_t alphaValue = (1 << image->depth) - 1;
         for (uint32_t y = 0; y < image->height; ++y) {
             uint8_t * const row = image->alphaPlane + y * image->alphaRowBytes;
@@ -130,7 +129,6 @@
     image->depth = depth;
     image->yuvFormat = yuvFormat;
     image->yuvRange = yuvRange;
-    image->alphaRange = AVIF_RANGE_FULL; // Unused by y4mRead() and y4mWrite().
     avifImageAllocatePlanes(image, createAlpha ? AVIF_PLANES_ALL : AVIF_PLANES_YUV);
     fillPlanes(image);
 
diff --git a/tests/avifyuv.c b/tests/avifyuv.c
index 2385bb0..76ac5bd 100644
--- a/tests/avifyuv.c
+++ b/tests/avifyuv.c
@@ -340,7 +340,6 @@
                         avifImageFreePlanes(image, AVIF_PLANES_ALL);
                         image->depth = yuvDepth;
                         image->yuvRange = yuvRange;
-                        image->alphaRange = AVIF_RANGE_FULL;
                         avifImageRGBToYUV(image, &srcRGB);
 
                         avifRGBImage intermediateRGB;