|
|
@@ -241,8 +241,8 @@ jsmpeg.prototype.decodeSequenceHeader = function() {
|
|
241
|
241
|
this.canvas.width = this.width;
|
|
242
|
242
|
this.canvas.height = this.height;
|
|
243
|
243
|
|
|
244
|
|
- this.currentRGB = this.canvasContext.getImageData(0, 0, this.width, this.height);
|
|
245
|
|
- this.fillArray(this.currentRGB.data, 255);
|
|
|
244
|
+ this.currentRGBA = this.canvasContext.getImageData(0, 0, this.width, this.height);
|
|
|
245
|
+ this.fillArray(this.currentRGBA.data, 255);
|
|
246
|
246
|
};
|
|
247
|
247
|
|
|
248
|
248
|
|
|
|
@@ -255,7 +255,7 @@ jsmpeg.prototype.currentY = null;
|
|
255
|
255
|
jsmpeg.prototype.currentCr = null;
|
|
256
|
256
|
jsmpeg.prototype.currentCb = null;
|
|
257
|
257
|
|
|
258
|
|
-jsmpeg.prototype.currentRGB = null;
|
|
|
258
|
+jsmpeg.prototype.currentRGBA = null;
|
|
259
|
259
|
|
|
260
|
260
|
jsmpeg.prototype.pictureCodingType = 0;
|
|
261
|
261
|
|
|
|
@@ -339,8 +339,8 @@ jsmpeg.prototype.decodePicture = function() {
|
|
339
|
339
|
this.buffer.rewind(32);
|
|
340
|
340
|
|
|
341
|
341
|
|
|
342
|
|
- this.YCrCbToRGB();
|
|
343
|
|
- this.canvasContext.putImageData(this.currentRGB, 0, 0);
|
|
|
342
|
+ this.YCrCbToRGBA();
|
|
|
343
|
+ this.canvasContext.putImageData(this.currentRGBA, 0, 0);
|
|
344
|
344
|
|
|
345
|
345
|
// If this is a reference picutre then rotate the prediction pointers
|
|
346
|
346
|
if( this.pictureCodingType == PICTURE_TYPE_I || this.pictureCodingType == PICTURE_TYPE_P ) {
|
|
|
@@ -353,61 +353,74 @@ jsmpeg.prototype.decodePicture = function() {
|
|
353
|
353
|
}
|
|
354
|
354
|
};
|
|
355
|
355
|
|
|
356
|
|
-jsmpeg.prototype.YCrCbToRGB = function() {
|
|
357
|
|
- // We process two lines at a time
|
|
358
|
|
- var size = this.codedSize >> 2;
|
|
359
|
|
-
|
|
360
|
|
- var index1 = 0;
|
|
361
|
|
- var rgbIndex1 = 0;
|
|
362
|
|
- var index2 = this.codedWidth;
|
|
363
|
|
- var rgbIndex2 = this.width * 4;
|
|
364
|
|
-
|
|
|
356
|
+jsmpeg.prototype.YCrCbToRGBA = function() {
|
|
365
|
357
|
var pY = this.currentY;
|
|
366
|
358
|
var pCr = this.currentCr;
|
|
367
|
359
|
var pCb = this.currentCb;
|
|
368
|
|
- var pRGB = this.currentRGB.data;
|
|
369
|
|
-
|
|
370
|
|
- var wrap = this.codedWidth + (this.codedWidth - this.width);
|
|
371
|
|
- var chromaWrap = this.halfWidth - (this.width >> 1);
|
|
372
|
|
- var rgbWrap = this.width * 4;
|
|
|
360
|
+ var pRGBA = this.currentRGBA.data;
|
|
|
361
|
+
|
|
|
362
|
+
|
|
|
363
|
+ // Chroma values are the same for each block of 4 pixels, so we proccess
|
|
|
364
|
+ // 2 lines at a time, 2 neighboring pixels each.
|
|
|
365
|
+
|
|
|
366
|
+ var yIndex1 = 0;
|
|
|
367
|
+ var yIndex2 = this.codedWidth;
|
|
|
368
|
+ var yNext2Lines = this.codedWidth + (this.codedWidth - this.width);
|
|
|
369
|
+
|
|
|
370
|
+ var cIndex = 0;
|
|
|
371
|
+ var cNextLine = this.halfWidth - (this.width >> 1);
|
|
|
372
|
+
|
|
|
373
|
+ var rgbaIndex1 = 0;
|
|
|
374
|
+ var rgbaIndex2 = this.width * 4;
|
|
|
375
|
+ var rgbaNext2Lines = this.width * 4;
|
|
373
|
376
|
|
|
374
|
|
- var y, cb, cr;
|
|
375
|
|
- for( var i = 0; i < size; i++ ) {
|
|
376
|
|
- cb = pCb[i] - 128;
|
|
377
|
|
- cr = pCr[i] - 128;
|
|
378
|
|
-
|
|
379
|
|
- y = pY[index1++];
|
|
380
|
|
- pRGB[rgbIndex1] = y + 1.4 * cr;
|
|
381
|
|
- pRGB[rgbIndex1+1] = y + -0.343 * cb - 0.711 * cr;
|
|
382
|
|
- pRGB[rgbIndex1+2] = y + 1.765 * cb;
|
|
383
|
|
- rgbIndex1+=4;
|
|
384
|
|
-
|
|
385
|
|
- y = pY[index1++];
|
|
386
|
|
- pRGB[rgbIndex1] = y + 1.4 * cr;
|
|
387
|
|
- pRGB[rgbIndex1+1] = y + -0.343 * cb - 0.711 * cr;
|
|
388
|
|
- pRGB[rgbIndex1+2] = y + 1.765 * cb;
|
|
389
|
|
- rgbIndex1+=4;
|
|
390
|
|
-
|
|
391
|
|
- y = pY[index2++];
|
|
392
|
|
- pRGB[rgbIndex2] = y + 1.4 * cr;
|
|
393
|
|
- pRGB[rgbIndex2+1] = y + -0.343 * cb - 0.711 * cr;
|
|
394
|
|
- pRGB[rgbIndex2+2] = y + 1.765 * cb;
|
|
395
|
|
- rgbIndex2+=4;
|
|
396
|
|
-
|
|
397
|
|
- y = pY[index2++];
|
|
398
|
|
- pRGB[rgbIndex2] = y + 1.4 * cr;
|
|
399
|
|
- pRGB[rgbIndex2+1] = y + -0.343 * cb - 0.711 * cr;
|
|
400
|
|
- pRGB[rgbIndex2+2] = y + 1.765 * cb;
|
|
401
|
|
- rgbIndex2+=4;
|
|
402
|
|
-
|
|
403
|
|
- // Next two lines
|
|
404
|
|
- if( rgbIndex1 % rgbWrap == 0 ) {
|
|
405
|
|
- i += chromaWrap;
|
|
406
|
|
- index1 += wrap;
|
|
407
|
|
- index2 += wrap;
|
|
408
|
|
- rgbIndex1 += rgbWrap;
|
|
409
|
|
- rgbIndex2 += rgbWrap;
|
|
|
377
|
+ var cols = this.width >> 1;
|
|
|
378
|
+ var rows = this.height >> 1;
|
|
|
379
|
+
|
|
|
380
|
+ var y, cb, cr, r, g, b;
|
|
|
381
|
+
|
|
|
382
|
+ for( var row = 0; row < rows; row++ ) {
|
|
|
383
|
+ for( var col = 0; col < cols; col++ ) {
|
|
|
384
|
+ cb = pCb[cIndex];
|
|
|
385
|
+ cr = pCr[cIndex];
|
|
|
386
|
+ cIndex++;
|
|
|
387
|
+
|
|
|
388
|
+ r = (cr + ((cr * 103) >> 8)) - 179;
|
|
|
389
|
+ g = ((cb * 88) >> 8) - 44 + ((cr * 183) >> 8) - 91;
|
|
|
390
|
+ b = (cb + ((cb * 198) >> 8)) - 227;
|
|
|
391
|
+
|
|
|
392
|
+ // Line 1
|
|
|
393
|
+ y = pY[yIndex1++];
|
|
|
394
|
+ pRGBA[rgbaIndex1] = y + r;
|
|
|
395
|
+ pRGBA[rgbaIndex1+1] = y - g;
|
|
|
396
|
+ pRGBA[rgbaIndex1+2] = y + b;
|
|
|
397
|
+ rgbaIndex1 += 4;
|
|
|
398
|
+
|
|
|
399
|
+ y = pY[yIndex1++];
|
|
|
400
|
+ pRGBA[rgbaIndex1] = y + r;
|
|
|
401
|
+ pRGBA[rgbaIndex1+1] = y - g;
|
|
|
402
|
+ pRGBA[rgbaIndex1+2] = y + b;
|
|
|
403
|
+ rgbaIndex1 += 4;
|
|
|
404
|
+
|
|
|
405
|
+ // Line 2
|
|
|
406
|
+ y = pY[yIndex2++];
|
|
|
407
|
+ pRGBA[rgbaIndex2] = y + r;
|
|
|
408
|
+ pRGBA[rgbaIndex2+1] = y - g;
|
|
|
409
|
+ pRGBA[rgbaIndex2+2] = y + b;
|
|
|
410
|
+ rgbaIndex2 += 4;
|
|
|
411
|
+
|
|
|
412
|
+ y = pY[yIndex2++];
|
|
|
413
|
+ pRGBA[rgbaIndex2] = y + r;
|
|
|
414
|
+ pRGBA[rgbaIndex2+1] = y - g;
|
|
|
415
|
+ pRGBA[rgbaIndex2+2] = y + b;
|
|
|
416
|
+ rgbaIndex2 += 4;
|
|
410
|
417
|
}
|
|
|
418
|
+
|
|
|
419
|
+ yIndex1 += yNext2Lines;
|
|
|
420
|
+ yIndex2 += yNext2Lines;
|
|
|
421
|
+ rgbaIndex1 += rgbaNext2Lines;
|
|
|
422
|
+ rgbaIndex2 += rgbaNext2Lines;
|
|
|
423
|
+ cIndex += cNextLine;
|
|
411
|
424
|
}
|
|
412
|
425
|
};
|
|
413
|
426
|
|