@@ -1022,6 +1022,81 @@ class EXRLoader extends DataTextureLoader {
1022
1022
1023
1023
}
1024
1024
1025
+ function lossyDctChannelDecode ( channelIndex , rowPtrs , channelData , acBuffer , dcBuffer , outBuffer ) {
1026
+
1027
+ const dataView = new DataView ( outBuffer . buffer ) ;
1028
+ const cd = channelData [ channelIndex ] ;
1029
+ const width = cd . width ;
1030
+ const height = cd . height ;
1031
+
1032
+ const numBlocksX = Math . ceil ( width / 8.0 ) ;
1033
+ const numBlocksY = Math . ceil ( height / 8.0 ) ;
1034
+ const numFullBlocksX = Math . floor ( width / 8.0 ) ;
1035
+ const leftoverX = width - ( numBlocksX - 1 ) * 8 ;
1036
+ const leftoverY = height - ( numBlocksY - 1 ) * 8 ;
1037
+
1038
+ const currAcComp = { value : 0 } ;
1039
+ let currDcComp = 0 ;
1040
+ const dctData = new Float32Array ( 64 ) ;
1041
+ const halfZigBlock = new Uint16Array ( 64 ) ;
1042
+ const rowBlock = new Uint16Array ( numBlocksX * 64 ) ;
1043
+
1044
+ for ( let blocky = 0 ; blocky < numBlocksY ; ++ blocky ) {
1045
+
1046
+ let maxY = 8 ;
1047
+
1048
+ if ( blocky == numBlocksY - 1 ) maxY = leftoverY ;
1049
+
1050
+ for ( let blockx = 0 ; blockx < numBlocksX ; ++ blockx ) {
1051
+
1052
+ halfZigBlock . fill ( 0 ) ;
1053
+ halfZigBlock [ 0 ] = dcBuffer [ currDcComp ++ ] ;
1054
+ unRleAC ( currAcComp , acBuffer , halfZigBlock ) ;
1055
+ unZigZag ( halfZigBlock , dctData ) ;
1056
+ dctInverse ( dctData ) ;
1057
+ convertToHalf ( dctData , rowBlock , blockx * 64 ) ;
1058
+
1059
+ }
1060
+
1061
+ // Write decoded data to output buffer
1062
+ for ( let y = 8 * blocky ; y < 8 * blocky + maxY ; ++ y ) {
1063
+
1064
+ let offset = rowPtrs [ channelIndex ] [ y ] ;
1065
+
1066
+ for ( let blockx = 0 ; blockx < numFullBlocksX ; ++ blockx ) {
1067
+
1068
+ const src = blockx * 64 + ( ( y & 0x7 ) * 8 ) ;
1069
+
1070
+ for ( let x = 0 ; x < 8 ; ++ x ) {
1071
+
1072
+ dataView . setUint16 ( offset + x * INT16_SIZE * cd . type , rowBlock [ src + x ] , true ) ;
1073
+
1074
+ }
1075
+
1076
+ offset += 8 * INT16_SIZE * cd . type ;
1077
+
1078
+ }
1079
+
1080
+ if ( numBlocksX != numFullBlocksX ) {
1081
+
1082
+ const src = numFullBlocksX * 64 + ( ( y & 0x7 ) * 8 ) ;
1083
+
1084
+ for ( let x = 0 ; x < leftoverX ; ++ x ) {
1085
+
1086
+ dataView . setUint16 ( offset + x * INT16_SIZE * cd . type , rowBlock [ src + x ] , true ) ;
1087
+
1088
+ }
1089
+
1090
+ }
1091
+
1092
+ }
1093
+
1094
+ }
1095
+
1096
+ cd . decoded = true ;
1097
+
1098
+ }
1099
+
1025
1100
function unRleAC ( currAcComp , acBuffer , halfZigBlock ) {
1026
1101
1027
1102
let acValue ;
@@ -1634,8 +1709,12 @@ class EXRLoader extends DataTextureLoader {
1634
1709
1635
1710
}
1636
1711
1637
- // Lossy DCT decode RGB channels
1638
- lossyDctDecode ( cscSet , rowOffsets , channelData , acBuffer , dcBuffer , outBuffer ) ;
1712
+ // Decode lossy DCT data if we have a valid color space conversion set with the first RGB channel present
1713
+ if ( cscSet . idx [ 0 ] !== undefined && channelData [ cscSet . idx [ 0 ] ] ) {
1714
+
1715
+ lossyDctDecode ( cscSet , rowOffsets , channelData , acBuffer , dcBuffer , outBuffer ) ;
1716
+
1717
+ }
1639
1718
1640
1719
// Decode other channels
1641
1720
for ( let i = 0 ; i < channelData . length ; ++ i ) {
@@ -1673,7 +1752,11 @@ class EXRLoader extends DataTextureLoader {
1673
1752
1674
1753
break ;
1675
1754
1676
- case LOSSY_DCT : // skip
1755
+ case LOSSY_DCT :
1756
+
1757
+ lossyDctChannelDecode ( i , rowOffsets , channelData , acBuffer , dcBuffer , outBuffer ) ;
1758
+
1759
+ break ;
1677
1760
1678
1761
default :
1679
1762
throw new Error ( 'EXRLoader.parse: unsupported channel compression' ) ;
0 commit comments