Renamed ispeWidth/ispeHeight to containerWidth/containerHeight; they now can hold tkhd's width/height
diff --git a/CHANGELOG.md b/CHANGELOG.md
index ad80749..1e982e4 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -5,6 +5,8 @@
 and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
 
 ## [Unreleased]
+### Changed
+- Renamed ispeWidth/ispeHeight to containerWidth/containerHeight; they now can hold tkhd's width/height
 
 ## [0.3.11] - 2019-09-26
 ### Added
diff --git a/include/avif/avif.h b/include/avif/avif.h
index 4427e30..f69a833 100644
--- a/include/avif/avif.h
+++ b/include/avif/avif.h
@@ -370,10 +370,15 @@
     double duration;               // in seconds (durationInTimescales / timescale)
     uint64_t durationInTimescales; // duration in "timescales"
 
-    // If decoding an "item" (instead of tracks) and the item is associated with an ImageSpatialExtentsBox,
-    // its values will be reflected here after a call to avifDecoderParse(), otherwise they will be set to 0.
-    uint32_t ispeWidth;
-    uint32_t ispeHeight;
+    // The width and height as reported by the AVIf container, if any. There is no guarantee
+    // these match the decoded images; they are merely reporting what is independently offered
+    // from the container's boxes.
+    // * If decoding an "item" and the item is associated with an ImageSpatialExtentsBox,
+    //   it will use the box's width/height
+    // * Else if decoding tracks, these will be the integer portions of the TrackHeaderBox width/height
+    // * Else both will be set to 0.
+    uint32_t containerWidth;
+    uint32_t containerHeight;
 
     // stats from the most recent read, possibly 0s if reading an image sequence
     avifIOStats ioStats;
diff --git a/src/read.c b/src/read.c
index 13b40fa..93feb80 100644
--- a/src/read.c
+++ b/src/read.c
@@ -194,6 +194,8 @@
     uint32_t auxForID; // if non-zero, this item is an auxC plane for Track #{auxForID}
     uint32_t mediaTimescale;
     uint64_t mediaDuration;
+    uint32_t width;
+    uint32_t height;
     avifSampleTable * sampleTable;
 } avifTrack;
 AVIF_ARRAY_DECLARE(avifTrackArray, avifTrack, track);
@@ -743,15 +745,35 @@
         CHECK(avifROStreamReadU64(&s, &ignored64)); // unsigned int(64) creation_time;
         CHECK(avifROStreamReadU64(&s, &ignored64)); // unsigned int(64) modification_time;
         CHECK(avifROStreamReadU32(&s, &trackID));   // unsigned int(32) track_ID;
+        CHECK(avifROStreamReadU32(&s, &ignored32)); // const unsigned int(32) reserved = 0;
+        CHECK(avifROStreamReadU64(&s, &ignored64)); // unsigned int(64) duration;
     } else if (version == 0) {
         CHECK(avifROStreamReadU32(&s, &ignored32)); // unsigned int(32) creation_time;
         CHECK(avifROStreamReadU32(&s, &ignored32)); // unsigned int(32) modification_time;
         CHECK(avifROStreamReadU32(&s, &trackID));   // unsigned int(32) track_ID;
+        CHECK(avifROStreamReadU32(&s, &ignored32)); // const unsigned int(32) reserved = 0;
+        CHECK(avifROStreamReadU32(&s, &ignored32)); // unsigned int(32) duration;
     } else {
         // Unsupported version
         return AVIF_FALSE;
     }
 
+    // Skipping the following 52 bytes here:
+    // ------------------------------------
+    // const unsigned int(32)[2] reserved = 0;
+    // template int(16) layer = 0;
+    // template int(16) alternate_group = 0;
+    // template int(16) volume = {if track_is_audio 0x0100 else 0};
+    // const unsigned int(16) reserved = 0;
+    // template int(32)[9] matrix= { 0x00010000,0,0,0,0x00010000,0,0,0,0x40000000 }; // unity matrix
+    CHECK(avifROStreamSkip(&s, 52));
+
+    uint32_t width, height;
+    CHECK(avifROStreamReadU32(&s, &width));  // unsigned int(32) width;
+    CHECK(avifROStreamReadU32(&s, &height)); // unsigned int(32) height;
+    track->width = width >> 16;
+    track->height = height >> 16;
+
     // TODO: support scaling based on width/height track header info?
 
     track->id = trackID;
@@ -1372,9 +1394,8 @@
         }
         memset(&decoder->imageTiming, 0, sizeof(decoder->imageTiming)); // to be set in avifDecoderNextImage()
 
-        // No ispe inside of a track
-        decoder->ispeWidth = 0;
-        decoder->ispeHeight = 0;
+        decoder->containerWidth = colorTrack->width;
+        decoder->containerHeight = colorTrack->height;
     } else {
         // Create from items
 
@@ -1467,11 +1488,11 @@
         decoder->ioStats.alphaOBUSize = alphaOBU.size;
 
         if (colorOBUItem->ispePresent) {
-            decoder->ispeWidth = colorOBUItem->ispe.width;
-            decoder->ispeHeight = colorOBUItem->ispe.height;
+            decoder->containerWidth = colorOBUItem->ispe.width;
+            decoder->containerHeight = colorOBUItem->ispe.height;
         } else {
-            decoder->ispeWidth = 0;
-            decoder->ispeHeight = 0;
+            decoder->containerWidth = 0;
+            decoder->containerHeight = 0;
         }
     }
 
@@ -1572,7 +1593,7 @@
         if (requestedIndex == decoder->imageIndex) {
             break;
         }
-    };
+    }
     return AVIF_RESULT_OK;
 }
 
diff --git a/tests/aviffuzz.c b/tests/aviffuzz.c
index 7704682..2db18ff 100644
--- a/tests/aviffuzz.c
+++ b/tests/aviffuzz.c
@@ -45,6 +45,7 @@
     // avifDecoderSetSource(decoder, AVIF_DECODER_SOURCE_PRIMARY_ITEM);
     avifResult result = avifDecoderParse(decoder, (avifROData *)&raw);
     if (result == AVIF_RESULT_OK) {
+        printf("AVIF container reports dimensions: %ux%u\n", decoder->containerWidth, decoder->containerHeight);
         for (int loop = 0; loop < 2; ++loop) {
             printf("Image decoded: %s\n", inputFilename);
             printf(" * %2.2f seconds, %d images\n", decoder->duration, decoder->imageCount);