Changeset 916 in SHVCSoftware for branches/SHM-upgrade/source/Lib/TLibVideoIO
- Timestamp:
- 12 Nov 2014, 08:09:17 (10 years ago)
- Location:
- branches/SHM-upgrade/source/Lib/TLibVideoIO
- Files:
-
- 2 edited
Legend:
- Unmodified
- Added
- Removed
-
branches/SHM-upgrade/source/Lib/TLibVideoIO/TVideoIOYuv.cpp
r823 r916 2 2 * License, included below. This software may be subject to other third party 3 3 * and contributor rights, including patent rights, and no such rights are 4 * granted under this license. 4 * granted under this license. 5 5 * 6 6 * Copyright (c) 2010-2014, ITU/ISO/IEC … … 42 42 #include <fstream> 43 43 #include <iostream> 44 #include <memory.h> 44 45 45 46 #include "TLibCommon/TComRom.h" … … 48 49 using namespace std; 49 50 50 /** 51 * Perform division with rounding of all pixels in img by 52 * 2<sup>shiftbits</sup>. All pixels are clipped to [minval, maxval] 53 * 54 * @param img pointer to image to be transformed 55 * @param stride distance between vertically adjacent pixels of img. 56 * @param width width of active area in img. 57 * @param height height of active area in img. 58 * @param shiftbits number of rounding bits 59 * @param minval minimum clipping value 60 * @param maxval maximum clipping value 61 */ 62 static void invScalePlane(Pel* img, UInt stride, UInt width, UInt height, 63 UInt shiftbits, Pel minval, Pel maxval) 64 { 65 Pel offset = 1 << (shiftbits-1); 66 for (UInt y = 0; y < height; y++) 67 { 68 for (UInt x = 0; x < width; x++) 69 { 70 Pel val = (img[x] + offset) >> shiftbits; 71 img[x] = Clip3(minval, maxval, val); 72 } 73 img += stride; 74 } 75 } 76 77 /** 78 * Multiply all pixels in img by 2<sup>shiftbits</sup>. 79 * 80 * @param img pointer to image to be transformed 81 * @param stride distance between vertically adjacent pixels of img. 82 * @param width width of active area in img. 83 * @param height height of active area in img. 84 * @param shiftbits number of bits to shift 85 */ 86 static void scalePlane(Pel* img, UInt stride, UInt width, UInt height, 87 UInt shiftbits) 88 { 89 for (UInt y = 0; y < height; y++) 90 { 91 for (UInt x = 0; x < width; x++) 92 { 93 img[x] <<= shiftbits; 94 } 95 img += stride; 96 } 97 } 51 // ==================================================================================================================== 52 // Local Functions 53 // ==================================================================================================================== 98 54 99 55 /** … … 112 68 * @param maxval maximum clipping value when dividing. 113 69 */ 114 static void scalePlane(Pel* img, UInt stride, UInt width, UInt height, 115 Int shiftbits, Pel minval, Pel maxval) 116 { 117 if (shiftbits == 0) 118 { 119 return; 120 } 121 70 static Void scalePlane(Pel* img, const UInt stride, const UInt width, const UInt height, Int shiftbits, Pel minval, Pel maxval) 71 { 122 72 if (shiftbits > 0) 123 73 { 124 scalePlane(img, stride, width, height, shiftbits); 125 } 126 else 127 { 128 invScalePlane(img, stride, width, height, -shiftbits, minval, maxval); 74 for (UInt y = 0; y < height; y++, img+=stride) 75 for (UInt x = 0; x < width; x++) 76 img[x] <<= shiftbits; 77 } 78 else if (shiftbits < 0) 79 { 80 shiftbits=-shiftbits; 81 82 Pel rounding = 1 << (shiftbits-1); 83 for (UInt y = 0; y < height; y++, img+=stride) 84 for (UInt x = 0; x < width; x++) 85 img[x] = Clip3(minval, maxval, Pel((img[x] + rounding) >> shiftbits)); 129 86 } 130 87 } … … 147 104 * \param pchFile file name string 148 105 * \param bWriteMode file open mode: true=read, false=write 149 * \param fileBitDepthY bit-depth of input/output file data (luma component). 150 * \param fileBitDepthC bit-depth of input/output file data (chroma components). 151 * \param internalBitDepthY bit-depth to scale image data to/from when reading/writing (luma component). 152 * \param internalBitDepthC bit-depth to scale image data to/from when reading/writing (chroma components). 106 * \param fileBitDepth bit-depth array of input/output file data. 107 * \param internalBitDepth bit-depth array to scale image data to/from when reading/writing. 153 108 */ 154 Void TVideoIOYuv::open( Char* pchFile, Bool bWriteMode, Int fileBitDepthY, Int fileBitDepthC, Int internalBitDepthY, Int internalBitDepthC) 155 { 156 m_bitDepthShiftY = internalBitDepthY - fileBitDepthY; 157 m_bitDepthShiftC = internalBitDepthC - fileBitDepthC; 158 m_fileBitDepthY = fileBitDepthY; 159 m_fileBitDepthC = fileBitDepthC; 109 Void TVideoIOYuv::open( Char* pchFile, Bool bWriteMode, const Int fileBitDepth[MAX_NUM_CHANNEL_TYPE], const Int MSBExtendedBitDepth[MAX_NUM_CHANNEL_TYPE], const Int internalBitDepth[MAX_NUM_CHANNEL_TYPE] ) 110 { 111 //NOTE: files cannot have bit depth greater than 16 112 for(UInt ch=0; ch<MAX_NUM_CHANNEL_TYPE; ch++) 113 { 114 m_fileBitdepth [ch] = std::min<UInt>(fileBitDepth[ch], 16); 115 m_MSBExtendedBitDepth[ch] = MSBExtendedBitDepth[ch]; 116 m_bitdepthShift [ch] = internalBitDepth[ch] - m_MSBExtendedBitDepth[ch]; 117 118 if (m_fileBitdepth[ch] > 16) 119 { 120 if (bWriteMode) 121 { 122 std::cerr << "\nWARNING: Cannot write a yuv file of bit depth greater than 16 - output will be right-shifted down to 16-bit precision\n" << std::endl; 123 } 124 else 125 { 126 std::cerr << "\nERROR: Cannot read a yuv file of bit depth greater than 16\n" << std::endl; 127 exit(0); 128 } 129 } 130 } 160 131 161 132 if ( bWriteMode ) 162 133 { 163 134 m_cHandle.open( pchFile, ios::binary | ios::out ); 164 135 165 136 if( m_cHandle.fail() ) 166 137 { … … 172 143 { 173 144 m_cHandle.open( pchFile, ios::binary | ios::in ); 174 145 175 146 if( m_cHandle.fail() ) 176 147 { … … 179 150 } 180 151 } 181 152 182 153 return; 183 154 } … … 204 175 * seekable, by consuming bytes. 205 176 */ 206 void TVideoIOYuv::skipFrames(UInt numFrames, UInt width, UInt height)177 Void TVideoIOYuv::skipFrames(UInt numFrames, UInt width, UInt height, ChromaFormat format) 207 178 { 208 179 if (!numFrames) 209 180 return; 210 181 211 const UInt wordsize = (m_fileBitDepthY > 8 || m_fileBitDepthC > 8) ? 2 : 1; 212 const streamoff framesize = wordsize * width * height * 3 / 2; 213 const streamoff offset = framesize * numFrames; 182 //------------------ 183 //set the frame size according to the chroma format 184 streamoff frameSize = 0; 185 UInt wordsize=1; // default to 8-bit, unless a channel with more than 8-bits is detected. 186 for (UInt component = 0; component < getNumberValidComponents(format); component++) 187 { 188 ComponentID compID=ComponentID(component); 189 frameSize += (width >> getComponentScaleX(compID, format)) * (height >> getComponentScaleY(compID, format)); 190 if (m_fileBitdepth[toChannelType(compID)] > 8) wordsize=2; 191 } 192 frameSize *= wordsize; 193 //------------------ 194 195 const streamoff offset = frameSize * numFrames; 214 196 215 197 /* attempt to seek */ … … 243 225 * @return true for success, false in case of error 244 226 */ 245 static Bool readPlane(Pel* dst, istream& fd, Bool is16bit, 246 UInt stride, 247 UInt width, UInt height, 248 UInt pad_x, UInt pad_y) 249 { 250 Int read_len = width * (is16bit ? 2 : 1); 251 UChar *buf = new UChar[read_len]; 252 for (Int y = 0; y < height; y++) 253 { 254 fd.read(reinterpret_cast<Char*>(buf), read_len); 255 if (fd.eof() || fd.fail() ) 256 { 257 delete[] buf; 258 return false; 259 } 260 261 if (!is16bit) 262 { 263 for (Int x = 0; x < width; x++) 264 { 265 dst[x] = buf[x]; 266 } 267 } 268 else 269 { 270 for (Int x = 0; x < width; x++) 271 { 272 dst[x] = (buf[2*x+1] << 8) | buf[2*x]; 273 } 274 } 275 276 for (Int x = width; x < width + pad_x; x++) 277 { 278 dst[x] = dst[width - 1]; 279 } 280 dst += stride; 281 } 282 for (Int y = height; y < height + pad_y; y++) 283 { 284 for (Int x = 0; x < width + pad_x; x++) 285 { 286 dst[x] = (dst - stride)[x]; 287 } 288 dst += stride; 227 static Bool readPlane(Pel* dst, 228 istream& fd, 229 Bool is16bit, 230 UInt stride444, 231 UInt width444, 232 UInt height444, 233 UInt pad_x444, 234 UInt pad_y444, 235 const ComponentID compID, 236 const ChromaFormat destFormat, 237 const ChromaFormat fileFormat, 238 const UInt fileBitDepth) 239 { 240 const UInt csx_file =getComponentScaleX(compID, fileFormat); 241 const UInt csy_file =getComponentScaleY(compID, fileFormat); 242 const UInt csx_dest =getComponentScaleX(compID, destFormat); 243 const UInt csy_dest =getComponentScaleY(compID, destFormat); 244 245 const UInt width_dest = width444 >>csx_dest; 246 const UInt height_dest = height444>>csy_dest; 247 const UInt pad_x_dest = pad_x444>>csx_dest; 248 const UInt pad_y_dest = pad_y444>>csy_dest; 249 const UInt stride_dest = stride444>>csx_dest; 250 251 const UInt full_width_dest = width_dest+pad_x_dest; 252 const UInt full_height_dest = height_dest+pad_y_dest; 253 254 const UInt stride_file = (width444 * (is16bit ? 2 : 1)) >> csx_file; 255 256 UChar *buf = new UChar[stride_file]; 257 258 if (compID!=COMPONENT_Y && (fileFormat==CHROMA_400 || destFormat==CHROMA_400)) 259 { 260 if (destFormat!=CHROMA_400) 261 { 262 // set chrominance data to mid-range: (1<<(fileBitDepth-1)) 263 const Pel value=Pel(1<<(fileBitDepth-1)); 264 for (UInt y = 0; y < full_height_dest; y++, dst+=stride_dest) 265 for (UInt x = 0; x < full_width_dest; x++) 266 dst[x] = value; 267 } 268 269 if (fileFormat!=CHROMA_400) 270 { 271 const UInt height_file = height444>>csy_file; 272 fd.seekg(height_file*stride_file, ios::cur); 273 if (fd.eof() || fd.fail() ) 274 { 275 delete[] buf; 276 return false; 277 } 278 } 279 } 280 else 281 { 282 const UInt mask_y_file=(1<<csy_file)-1; 283 const UInt mask_y_dest=(1<<csy_dest)-1; 284 for(UInt y444=0; y444<height444; y444++) 285 { 286 if ((y444&mask_y_file)==0) 287 { 288 // read a new line 289 fd.read(reinterpret_cast<Char*>(buf), stride_file); 290 if (fd.eof() || fd.fail() ) 291 { 292 delete[] buf; 293 return false; 294 } 295 } 296 297 if ((y444&mask_y_dest)==0) 298 { 299 // process current destination line 300 if (csx_file < csx_dest) 301 { 302 // eg file is 444, dest is 422. 303 const UInt sx=csx_dest-csx_file; 304 if (!is16bit) 305 { 306 for (UInt x = 0; x < width_dest; x++) 307 dst[x] = buf[x<<sx]; 308 } 309 else 310 { 311 for (UInt x = 0; x < width_dest; x++) 312 { 313 dst[x] = Pel(buf[(x<<sx)*2+0]) | (Pel(buf[(x<<sx)*2+1])<<8); 314 } 315 } 316 } 317 else 318 { 319 // eg file is 422, dest is 444. 320 const UInt sx=csx_file-csx_dest; 321 if (!is16bit) 322 { 323 for (UInt x = 0; x < width_dest; x++) 324 dst[x] = buf[x>>sx]; 325 } 326 else 327 { 328 for (UInt x = 0; x < width_dest; x++) 329 dst[x] = Pel(buf[(x>>sx)*2+0]) | (Pel(buf[(x>>sx)*2+1])<<8); 330 } 331 } 332 333 // process right hand side padding 334 const Pel val=dst[width_dest-1]; 335 for (UInt x = width_dest; x < full_width_dest; x++) 336 dst[x] = val; 337 338 dst += stride_dest; 339 } 340 } 341 342 // process lower padding 343 for (UInt y = height_dest; y < full_height_dest; y++, dst+=stride_dest) 344 for (UInt x = 0; x < full_width_dest; x++) 345 dst[x] = (dst - stride_dest)[x]; 289 346 } 290 347 delete[] buf; … … 304 361 */ 305 362 static Bool writePlane(ostream& fd, Pel* src, Bool is16bit, 306 UInt stride, 307 UInt width, UInt height) 308 { 309 Int write_len = width * (is16bit ? 2 : 1); 310 UChar *buf = new UChar[write_len]; 311 for (Int y = 0; y < height; y++) 312 { 313 if (!is16bit) 314 { 315 for (Int x = 0; x < width; x++) 316 { 317 buf[x] = (UChar) src[x]; 318 } 319 } 320 else 321 { 322 for (Int x = 0; x < width; x++) 323 { 324 buf[2*x] = src[x] & 0xff; 325 buf[2*x+1] = (src[x] >> 8) & 0xff; 326 } 327 } 328 329 fd.write(reinterpret_cast<Char*>(buf), write_len); 330 if (fd.eof() || fd.fail() ) 331 { 332 delete[] buf; 333 return false; 334 } 335 src += stride; 363 UInt stride444, 364 UInt width444, UInt height444, 365 const ComponentID compID, 366 const ChromaFormat srcFormat, 367 const ChromaFormat fileFormat, 368 const UInt fileBitDepth) 369 { 370 const UInt csx_file =getComponentScaleX(compID, fileFormat); 371 const UInt csy_file =getComponentScaleY(compID, fileFormat); 372 const UInt csx_src =getComponentScaleX(compID, srcFormat); 373 const UInt csy_src =getComponentScaleY(compID, srcFormat); 374 375 const UInt stride_src = stride444>>csx_src; 376 377 const UInt stride_file = (width444 * (is16bit ? 2 : 1)) >> csx_file; 378 const UInt width_file = width444 >>csx_file; 379 const UInt height_file = height444>>csy_file; 380 381 UChar *buf = new UChar[stride_file]; 382 383 if (compID!=COMPONENT_Y && (fileFormat==CHROMA_400 || srcFormat==CHROMA_400)) 384 { 385 if (fileFormat!=CHROMA_400) 386 { 387 const UInt value=1<<(fileBitDepth-1); 388 389 for(UInt y=0; y< height_file; y++) 390 { 391 if (!is16bit) 392 { 393 UChar val(value); 394 for (UInt x = 0; x < width_file; x++) 395 buf[x]=val; 396 } 397 else 398 { 399 UShort val(value); 400 for (UInt x = 0; x < width_file; x++) 401 { 402 buf[2*x+0]= (val>>0) & 0xff; 403 buf[2*x+1]= (val>>8) & 0xff; 404 } 405 } 406 407 fd.write(reinterpret_cast<Char*>(buf), stride_file); 408 if (fd.eof() || fd.fail() ) 409 { 410 delete[] buf; 411 return false; 412 } 413 } 414 } 415 } 416 else 417 { 418 const UInt mask_y_file=(1<<csy_file)-1; 419 const UInt mask_y_src =(1<<csy_src )-1; 420 for(UInt y444=0; y444<height444; y444++) 421 { 422 if ((y444&mask_y_file)==0) 423 { 424 // write a new line 425 if (csx_file < csx_src) 426 { 427 // eg file is 444, source is 422. 428 const UInt sx=csx_src-csx_file; 429 if (!is16bit) 430 { 431 for (UInt x = 0; x < width_file; x++) 432 { 433 buf[x] = (UChar)(src[x>>sx]); 434 } 435 } 436 else 437 { 438 for (UInt x = 0; x < width_file; x++) 439 { 440 buf[2*x ] = (src[x>>sx]>>0) & 0xff; 441 buf[2*x+1] = (src[x>>sx]>>8) & 0xff; 442 } 443 } 444 } 445 else 446 { 447 // eg file is 422, src is 444. 448 const UInt sx=csx_file-csx_src; 449 if (!is16bit) 450 { 451 for (UInt x = 0; x < width_file; x++) 452 { 453 buf[x] = (UChar)(src[x<<sx]); 454 } 455 } 456 else 457 { 458 for (UInt x = 0; x < width_file; x++) 459 { 460 buf[2*x ] = (src[x<<sx]>>0) & 0xff; 461 buf[2*x+1] = (src[x<<sx]>>8) & 0xff; 462 } 463 } 464 } 465 466 fd.write(reinterpret_cast<Char*>(buf), stride_file); 467 if (fd.eof() || fd.fail() ) 468 { 469 delete[] buf; 470 return false; 471 } 472 } 473 474 if ((y444&mask_y_src)==0) 475 { 476 src += stride_src; 477 } 478 479 } 336 480 } 337 481 delete[] buf; … … 340 484 341 485 static Bool writeField(ostream& fd, Pel* top, Pel* bottom, Bool is16bit, 342 UInt stride, 343 UInt width, UInt height, bool isTff) 344 { 345 Int write_len = width * (is16bit ? 2 : 1)*2; 346 UChar *buf = new UChar[write_len]; 347 for (Int y = 0; y < height; y++) 348 { 349 if (!is16bit) 350 { 351 for (Int x = 0; x < width; x++) 352 { 353 buf[x] = isTff ? (UChar) top[x] : (UChar) bottom[x]; 354 buf[width+x] = isTff ? (UChar) bottom[x] : (UChar) top[x]; 355 } 356 } 357 else 358 { 359 for (Int x = 0; x < width; x++) 360 { 361 buf[2*x] = isTff ? top[x] & 0xff : bottom[x] & 0xff; 362 buf[2*x+1] = isTff ? (top[x] >> 8) & 0xff : (bottom[x] >> 8) & 0xff; 363 364 buf[width+2*x] = isTff ? bottom[x] & 0xff : top[x] & 0xff; 365 buf[width+2*x+1] = isTff ? (bottom[x] >> 8) & 0xff : (top[x] >> 8) & 0xff; 366 } 367 } 368 369 fd.write(reinterpret_cast<Char*>(buf), write_len); 370 if (fd.eof() || fd.fail() ) 371 { 372 delete[] buf; 373 return false; 374 } 375 top += stride; 376 bottom += stride; 486 UInt stride444, 487 UInt width444, UInt height444, 488 const ComponentID compID, 489 const ChromaFormat srcFormat, 490 const ChromaFormat fileFormat, 491 const UInt fileBitDepth, const Bool isTff) 492 { 493 const UInt csx_file =getComponentScaleX(compID, fileFormat); 494 const UInt csy_file =getComponentScaleY(compID, fileFormat); 495 const UInt csx_src =getComponentScaleX(compID, srcFormat); 496 const UInt csy_src =getComponentScaleY(compID, srcFormat); 497 498 const UInt stride_src = stride444>>csx_src; 499 500 const UInt stride_file = (width444 * (is16bit ? 2 : 1)) >> csx_file; 501 const UInt width_file = width444 >>csx_file; 502 const UInt height_file = height444>>csy_file; 503 504 UChar *buf = new UChar[stride_file * 2]; 505 506 if (compID!=COMPONENT_Y && (fileFormat==CHROMA_400 || srcFormat==CHROMA_400)) 507 { 508 if (fileFormat!=CHROMA_400) 509 { 510 const UInt value=1<<(fileBitDepth-1); 511 512 for(UInt y=0; y< height_file; y++) 513 { 514 for (UInt field = 0; field < 2; field++) 515 { 516 UChar *fieldBuffer = buf + (field * stride_file); 517 518 if (!is16bit) 519 { 520 UChar val(value); 521 for (UInt x = 0; x < width_file; x++) 522 fieldBuffer[x]=val; 523 } 524 else 525 { 526 UShort val(value); 527 for (UInt x = 0; x < width_file; x++) 528 { 529 fieldBuffer[2*x+0]= (val>>0) & 0xff; 530 fieldBuffer[2*x+1]= (val>>8) & 0xff; 531 } 532 } 533 } 534 535 fd.write(reinterpret_cast<Char*>(buf), (stride_file * 2)); 536 if (fd.eof() || fd.fail() ) 537 { 538 delete[] buf; 539 return false; 540 } 541 } 542 } 543 } 544 else 545 { 546 const UInt mask_y_file=(1<<csy_file)-1; 547 const UInt mask_y_src =(1<<csy_src )-1; 548 for(UInt y444=0; y444<height444; y444++) 549 { 550 if ((y444&mask_y_file)==0) 551 { 552 for (UInt field = 0; field < 2; field++) 553 { 554 UChar *fieldBuffer = buf + (field * stride_file); 555 Pel *src = (((field == 0) && isTff) || ((field == 1) && (!isTff))) ? top : bottom; 556 557 // write a new line 558 if (csx_file < csx_src) 559 { 560 // eg file is 444, source is 422. 561 const UInt sx=csx_src-csx_file; 562 if (!is16bit) 563 { 564 for (UInt x = 0; x < width_file; x++) 565 { 566 fieldBuffer[x] = (UChar)(src[x>>sx]); 567 } 568 } 569 else 570 { 571 for (UInt x = 0; x < width_file; x++) 572 { 573 fieldBuffer[2*x ] = (src[x>>sx]>>0) & 0xff; 574 fieldBuffer[2*x+1] = (src[x>>sx]>>8) & 0xff; 575 } 576 } 577 } 578 else 579 { 580 // eg file is 422, src is 444. 581 const UInt sx=csx_file-csx_src; 582 if (!is16bit) 583 { 584 for (UInt x = 0; x < width_file; x++) 585 { 586 fieldBuffer[x] = (UChar)(src[x<<sx]); 587 } 588 } 589 else 590 { 591 for (UInt x = 0; x < width_file; x++) 592 { 593 fieldBuffer[2*x ] = (src[x<<sx]>>0) & 0xff; 594 fieldBuffer[2*x+1] = (src[x<<sx]>>8) & 0xff; 595 } 596 } 597 } 598 } 599 600 fd.write(reinterpret_cast<Char*>(buf), (stride_file * 2)); 601 if (fd.eof() || fd.fail() ) 602 { 603 delete[] buf; 604 return false; 605 } 606 } 607 608 if ((y444&mask_y_src)==0) 609 { 610 top += stride_src; 611 bottom += stride_src; 612 } 613 614 } 377 615 } 378 616 delete[] buf; 379 617 return true; 380 618 } 619 381 620 /** 382 621 * Read one Y'CbCr frame, performing any required input scaling to change … … 392 631 * @return true for success, false in case of error 393 632 */ 394 Bool TVideoIOYuv::read ( TComPicYuv* pPicYuv , Int aiPad[2])633 Bool TVideoIOYuv::read ( TComPicYuv* pPicYuvUser, TComPicYuv* pPicYuvTrueOrg, const InputColourSpaceConversion ipcsc, Int aiPad[2], ChromaFormat format ) 395 634 { 396 635 // check end-of-file 397 636 if ( isEof() ) return false; 398 399 Int iStride = pPicYuv->getStride(); 400 637 TComPicYuv *pPicYuv=pPicYuvTrueOrg; 638 if (format>=NUM_CHROMA_FORMAT) format=pPicYuv->getChromaFormat(); 639 640 Bool is16bit = false; 641 642 for(UInt ch=0; ch<MAX_NUM_CHANNEL_TYPE; ch++) 643 { 644 if (m_fileBitdepth[ch] > 8) is16bit=true; 645 } 646 647 const UInt stride444 = pPicYuv->getStride(COMPONENT_Y); 648 401 649 // compute actual YUV width & height excluding padding size 402 UInt pad_h = aiPad[0]; 403 UInt pad_v = aiPad[1]; 404 UInt width_full = pPicYuv->getWidth(); 405 UInt height_full = pPicYuv->getHeight(); 406 UInt width = width_full - pad_h; 407 UInt height = height_full - pad_v; 408 Bool is16bit = m_fileBitDepthY > 8 || m_fileBitDepthC > 8; 409 410 Int desired_bitdepthY = m_fileBitDepthY + m_bitDepthShiftY; 411 Int desired_bitdepthC = m_fileBitDepthC + m_bitDepthShiftC; 412 Pel minvalY = 0; 413 Pel minvalC = 0; 414 Pel maxvalY = (1 << desired_bitdepthY) - 1; 415 Pel maxvalC = (1 << desired_bitdepthC) - 1; 416 #if CLIP_TO_709_RANGE 417 if (m_bitdepthShiftY < 0 && desired_bitdepthY >= 8) 418 { 419 /* ITU-R BT.709 compliant clipping for converting say 10b to 8b */ 420 minvalY = 1 << (desired_bitdepthY - 8); 421 maxvalY = (0xff << (desired_bitdepthY - 8)) -1; 422 } 423 if (m_bitdepthShiftC < 0 && desired_bitdepthC >= 8) 424 { 425 /* ITU-R BT.709 compliant clipping for converting say 10b to 8b */ 426 minvalC = 1 << (desired_bitdepthC - 8); 427 maxvalC = (0xff << (desired_bitdepthC - 8)) -1; 428 } 650 const UInt pad_h444 = aiPad[0]; 651 const UInt pad_v444 = aiPad[1]; 652 653 const UInt width_full444 = pPicYuv->getWidth(COMPONENT_Y); 654 const UInt height_full444 = pPicYuv->getHeight(COMPONENT_Y); 655 656 const UInt width444 = width_full444 - pad_h444; 657 const UInt height444 = height_full444 - pad_v444; 658 659 for(UInt comp=0; comp<MAX_NUM_COMPONENT; comp++) 660 { 661 const ComponentID compID = ComponentID(comp); 662 const ChannelType chType=toChannelType(compID); 663 664 const Int desired_bitdepth = m_MSBExtendedBitDepth[chType] + m_bitdepthShift[chType]; 665 666 #if !CLIP_TO_709_RANGE 667 const Pel minval = 0; 668 const Pel maxval = (1 << desired_bitdepth) - 1; 669 #else 670 const Bool b709Compliance=(m_bitdepthShift[chType] < 0 && desired_bitdepth >= 8); /* ITU-R BT.709 compliant clipping for converting say 10b to 8b */ 671 const Pel minval = b709Compliance? (( 1 << (desired_bitdepth - 8)) ) : 0; 672 const Pel maxval = b709Compliance? ((0xff << (desired_bitdepth - 8)) -1) : (1 << desired_bitdepth) - 1; 429 673 #endif 430 431 if (! readPlane(pPicYuv->getLumaAddr(), m_cHandle, is16bit, iStride, width, height, pad_h, pad_v))432 return false;433 scalePlane(pPicYuv->getLumaAddr(), iStride, width_full, height_full, m_bitDepthShiftY, minvalY, maxvalY);434 435 iStride >>= 1; 436 width_full >>= 1;437 height_full >>= 1;438 width >>= 1;439 height >>= 1;440 pad_h >>= 1;441 pad_v >>= 1;442 443 if (! readPlane(pPicYuv->getCbAddr(), m_cHandle, is16bit, iStride, width, height, pad_h, pad_v)) 444 return false;445 scalePlane(pPicYuv->getCbAddr(), iStride, width_full, height_full, m_bitDepthShiftC, minvalC, maxvalC);446 447 if (! readPlane(pPicYuv->getCrAddr(), m_cHandle, is16bit, iStride, width, height, pad_h, pad_v))448 return false;449 scalePlane(pPicYuv->getCrAddr(), iStride, width_full, height_full, m_bitDepthShiftC, minvalC, maxvalC);674 675 if (! readPlane(pPicYuv->getAddr(compID), m_cHandle, is16bit, stride444, width444, height444, pad_h444, pad_v444, compID, pPicYuv->getChromaFormat(), format, m_fileBitdepth[chType])) 676 { 677 return false; 678 } 679 680 if (compID < pPicYuv->getNumberValidComponents() ) 681 { 682 const UInt csx=getComponentScaleX(compID, pPicYuv->getChromaFormat()); 683 const UInt csy=getComponentScaleY(compID, pPicYuv->getChromaFormat()); 684 scalePlane(pPicYuv->getAddr(compID), stride444>>csx, width_full444>>csx, height_full444>>csy, m_bitdepthShift[chType], minval, maxval); 685 } 686 } 687 688 Int internalBitDepth[MAX_NUM_CHANNEL_TYPE]; 689 for(UInt chType=0; chType<MAX_NUM_CHANNEL_TYPE; chType++) 690 { 691 internalBitDepth[chType] = m_bitdepthShift[chType] + m_MSBExtendedBitDepth[chType]; 692 } 693 ColourSpaceConvert(*pPicYuvTrueOrg, *pPicYuvUser, ipcsc, internalBitDepth, true); 450 694 451 695 return true; … … 460 704 * @return true for success, false in case of error 461 705 */ 462 Bool TVideoIOYuv::write( TComPicYuv* pPicYuv, Int confLeft, Int confRight, Int confTop, Int confBottom ) 463 { 706 Bool TVideoIOYuv::write( TComPicYuv* pPicYuvUser, const InputColourSpaceConversion ipCSC, Int confLeft, Int confRight, Int confTop, Int confBottom, ChromaFormat format ) 707 { 708 TComPicYuv cPicYuvCSCd; 709 if (ipCSC!=IPCOLOURSPACE_UNCHANGED) 710 { 711 cPicYuvCSCd.create(pPicYuvUser->getWidth(COMPONENT_Y), pPicYuvUser->getHeight(COMPONENT_Y), pPicYuvUser->getChromaFormat(), g_uiMaxCUWidth, g_uiMaxCUHeight, g_uiMaxCUDepth); 712 Int internalBitDepth[MAX_NUM_CHANNEL_TYPE]; 713 for(UInt chType=0; chType<MAX_NUM_CHANNEL_TYPE; chType++) 714 { 715 internalBitDepth[chType] = m_bitdepthShift[chType] + m_MSBExtendedBitDepth[chType]; 716 } 717 ColourSpaceConvert(*pPicYuvUser, cPicYuvCSCd, ipCSC, internalBitDepth, false); 718 } 719 TComPicYuv *pPicYuv=(ipCSC==IPCOLOURSPACE_UNCHANGED) ? pPicYuvUser : &cPicYuvCSCd; 720 464 721 // compute actual YUV frame size excluding padding size 465 Int iStride = pPicYuv->getStride(); 466 UInt width = pPicYuv->getWidth() - confLeft - confRight; 467 UInt height = pPicYuv->getHeight() - confTop - confBottom; 468 Bool is16bit = m_fileBitDepthY > 8 || m_fileBitDepthC > 8; 722 const Int iStride444 = pPicYuv->getStride(COMPONENT_Y); 723 const UInt width444 = pPicYuv->getWidth(COMPONENT_Y) - confLeft - confRight; 724 const UInt height444 = pPicYuv->getHeight(COMPONENT_Y) - confTop - confBottom; 725 Bool is16bit = false; 726 Bool nonZeroBitDepthShift=false; 727 728 if ((width444 == 0) || (height444 == 0)) 729 { 730 printf ("\nWarning: writing %d x %d luma sample output picture!", width444, height444); 731 } 732 733 for(UInt ch=0; ch<MAX_NUM_CHANNEL_TYPE; ch++) 734 { 735 if (m_fileBitdepth[ch] > 8) is16bit=true; 736 if (m_bitdepthShift[ch] != 0) nonZeroBitDepthShift=true; 737 } 738 469 739 TComPicYuv *dstPicYuv = NULL; 470 740 Bool retval = true; 471 472 if ((width==0)||(height==0)) 473 { 474 printf ("\nWarning: writing %d x %d luma sample output picture!", width, height); 475 } 476 477 if (m_bitDepthShiftY != 0 || m_bitDepthShiftC != 0) 741 if (format>=NUM_CHROMA_FORMAT) format=pPicYuv->getChromaFormat(); 742 743 if (nonZeroBitDepthShift) 478 744 { 479 745 dstPicYuv = new TComPicYuv; 480 #if AUXILIARY_PICTURES 481 dstPicYuv->create( pPicYuv->getWidth(), pPicYuv->getHeight(), pPicYuv->getChromaFormat(), 1, 1, 0 ); 746 dstPicYuv->create( pPicYuv->getWidth(COMPONENT_Y), pPicYuv->getHeight(COMPONENT_Y), pPicYuv->getChromaFormat(), 1, 1, 0 ); 747 pPicYuv->copyToPic(dstPicYuv); 748 749 for(UInt comp=0; comp<dstPicYuv->getNumberValidComponents(); comp++) 750 { 751 const ComponentID compID=ComponentID(comp); 752 const ChannelType ch=toChannelType(compID); 753 #if !CLIP_TO_709_RANGE 754 const Pel minval = 0; 755 const Pel maxval = (1 << m_MSBExtendedBitDepth[ch]) - 1; 482 756 #else 483 dstPicYuv->create( pPicYuv->getWidth(), pPicYuv->getHeight(), 1, 1, 0 ); 757 const Bool b709Compliance=(-m_bitdepthShift[ch] < 0 && m_MSBExtendedBitDepth[ch] >= 8); /* ITU-R BT.709 compliant clipping for converting say 10b to 8b */ 758 const Pel minval = b709Compliance? (( 1 << (m_MSBExtendedBitDepth[ch] - 8)) ) : 0; 759 const Pel maxval = b709Compliance? ((0xff << (m_MSBExtendedBitDepth[ch] - 8)) -1) : (1 << m_MSBExtendedBitDepth[ch]) - 1; 484 760 #endif 485 pPicYuv->copyToPic(dstPicYuv); 486 487 Pel minvalY = 0; 488 Pel minvalC = 0; 489 Pel maxvalY = (1 << m_fileBitDepthY) - 1; 490 Pel maxvalC = (1 << m_fileBitDepthC) - 1; 491 #if CLIP_TO_709_RANGE 492 if (-m_bitDepthShiftY < 0 && m_fileBitDepthY >= 8) 493 { 494 /* ITU-R BT.709 compliant clipping for converting say 10b to 8b */ 495 minvalY = 1 << (m_fileBitDepthY - 8); 496 maxvalY = (0xff << (m_fileBitDepthY - 8)) -1; 497 } 498 if (-m_bitDepthShiftC < 0 && m_fileBitDepthC >= 8) 499 { 500 /* ITU-R BT.709 compliant clipping for converting say 10b to 8b */ 501 minvalC = 1 << (m_fileBitDepthC - 8); 502 maxvalC = (0xff << (m_fileBitDepthC - 8)) -1; 503 } 504 #endif 505 scalePlane(dstPicYuv->getLumaAddr(), dstPicYuv->getStride(), dstPicYuv->getWidth(), dstPicYuv->getHeight(), -m_bitDepthShiftY, minvalY, maxvalY); 506 scalePlane(dstPicYuv->getCbAddr(), dstPicYuv->getCStride(), dstPicYuv->getWidth()>>1, dstPicYuv->getHeight()>>1, -m_bitDepthShiftC, minvalC, maxvalC); 507 scalePlane(dstPicYuv->getCrAddr(), dstPicYuv->getCStride(), dstPicYuv->getWidth()>>1, dstPicYuv->getHeight()>>1, -m_bitDepthShiftC, minvalC, maxvalC); 761 762 scalePlane(dstPicYuv->getAddr(compID), dstPicYuv->getStride(compID), dstPicYuv->getWidth(compID), dstPicYuv->getHeight(compID), -m_bitdepthShift[ch], minval, maxval); 763 } 508 764 } 509 765 else … … 511 767 dstPicYuv = pPicYuv; 512 768 } 513 // location of upper left pel in a plane 514 Int planeOffset = confLeft + confTop * iStride; 515 516 if (! writePlane(m_cHandle, dstPicYuv->getLumaAddr() + planeOffset, is16bit, iStride, width, height)) 517 { 518 retval=false; 519 goto exit; 520 } 521 522 width >>= 1; 523 height >>= 1; 524 iStride >>= 1; 525 confLeft >>= 1; 526 confRight >>= 1; 527 confTop >>= 1; 528 confBottom >>= 1; 529 530 planeOffset = confLeft + confTop * iStride; 531 532 if (! writePlane(m_cHandle, dstPicYuv->getCbAddr() + planeOffset, is16bit, iStride, width, height)) 533 { 534 retval=false; 535 goto exit; 536 } 537 if (! writePlane(m_cHandle, dstPicYuv->getCrAddr() + planeOffset, is16bit, iStride, width, height)) 538 { 539 retval=false; 540 goto exit; 541 } 542 543 exit: 544 if (m_bitDepthShiftY != 0 || m_bitDepthShiftC != 0) 769 770 for(UInt comp=0; retval && comp<dstPicYuv->getNumberValidComponents(); comp++) 771 { 772 const ComponentID compID = ComponentID(comp); 773 const ChannelType ch=toChannelType(compID); 774 const UInt csx = pPicYuv->getComponentScaleX(compID); 775 const UInt csy = pPicYuv->getComponentScaleY(compID); 776 const Int planeOffset = (confLeft>>csx) + (confTop>>csy) * pPicYuv->getStride(compID); 777 if (! writePlane(m_cHandle, dstPicYuv->getAddr(compID) + planeOffset, is16bit, iStride444, width444, height444, compID, dstPicYuv->getChromaFormat(), format, m_fileBitdepth[ch])) 778 { 779 retval=false; 780 } 781 } 782 783 if (nonZeroBitDepthShift) 545 784 { 546 785 dstPicYuv->destroy(); 547 786 delete dstPicYuv; 548 } 787 } 788 789 cPicYuvCSCd.destroy(); 790 549 791 return retval; 550 792 } 551 793 552 553 /** 554 * Write one Y'CbCr frame. No bit-depth conversion is performed, pcPicYuv is 555 * assumed to be at TVideoIO::m_fileBitdepth depth. 556 * 557 * @param pPicTop input top field YUV buffer class pointer 558 * @param pPicBottom input bottom field YUV buffer class pointer 559 * @param aiPad source padding size, aiPad[0] = horizontal, aiPad[1] = vertical 560 * @return true for success, false in case of error 561 */ 562 Bool TVideoIOYuv::write( TComPicYuv* pPicTop, TComPicYuv* pPicBottom, Int cropLeft, Int cropRight, Int cropTop, Int cropBottom , bool isTff) 563 { 564 // compute actual YUV frame size excluding padding size 565 Int iStride = pPicTop->getStride(); 566 UInt width = pPicTop->getWidth() - cropLeft - cropRight; 567 UInt height = pPicTop->getHeight() - cropTop - cropBottom; 568 Bool is16bit = m_fileBitDepthY > 8 || m_fileBitDepthC > 8; 569 570 TComPicYuv *dstPicTop = NULL; 571 TComPicYuv *dstPicBottom = NULL; 572 794 Bool TVideoIOYuv::write( TComPicYuv* pPicYuvUserTop, TComPicYuv* pPicYuvUserBottom, const InputColourSpaceConversion ipCSC, Int confLeft, Int confRight, Int confTop, Int confBottom, ChromaFormat format, const Bool isTff ) 795 { 796 797 TComPicYuv cPicYuvTopCSCd; 798 TComPicYuv cPicYuvBottomCSCd; 799 if (ipCSC!=IPCOLOURSPACE_UNCHANGED) 800 { 801 cPicYuvTopCSCd .create(pPicYuvUserTop ->getWidth(COMPONENT_Y), pPicYuvUserTop ->getHeight(COMPONENT_Y), pPicYuvUserTop ->getChromaFormat(), g_uiMaxCUWidth, g_uiMaxCUHeight, g_uiMaxCUDepth); 802 cPicYuvBottomCSCd.create(pPicYuvUserBottom->getWidth(COMPONENT_Y), pPicYuvUserBottom->getHeight(COMPONENT_Y), pPicYuvUserBottom->getChromaFormat(), g_uiMaxCUWidth, g_uiMaxCUHeight, g_uiMaxCUDepth); 803 Int internalBitDepth[MAX_NUM_CHANNEL_TYPE]; 804 for(UInt chType=0; chType<MAX_NUM_CHANNEL_TYPE; chType++) 805 { 806 internalBitDepth[chType] = m_bitdepthShift[chType] + m_MSBExtendedBitDepth[chType]; 807 } 808 ColourSpaceConvert(*pPicYuvUserTop, cPicYuvTopCSCd, ipCSC, internalBitDepth, false); 809 ColourSpaceConvert(*pPicYuvUserBottom, cPicYuvBottomCSCd, ipCSC, internalBitDepth, false); 810 } 811 TComPicYuv *pPicYuvTop = (ipCSC==IPCOLOURSPACE_UNCHANGED) ? pPicYuvUserTop : &cPicYuvTopCSCd; 812 TComPicYuv *pPicYuvBottom = (ipCSC==IPCOLOURSPACE_UNCHANGED) ? pPicYuvUserBottom : &cPicYuvBottomCSCd; 813 814 Bool is16bit = false; 815 Bool nonZeroBitDepthShift=false; 816 817 for(UInt ch=0; ch<MAX_NUM_CHANNEL_TYPE; ch++) 818 { 819 if (m_fileBitdepth[ch] > 8) is16bit=true; 820 if (m_bitdepthShift[ch] != 0) nonZeroBitDepthShift=true; 821 } 822 823 TComPicYuv *dstPicYuvTop = NULL; 824 TComPicYuv *dstPicYuvBottom = NULL; 825 826 for (UInt field = 0; field < 2; field++) 827 { 828 TComPicYuv *pPicYuv = (field == 0) ? pPicYuvTop : pPicYuvBottom; 829 830 if (format>=NUM_CHROMA_FORMAT) format=pPicYuv->getChromaFormat(); 831 832 TComPicYuv* &dstPicYuv = (field == 0) ? dstPicYuvTop : dstPicYuvBottom; 833 834 if (nonZeroBitDepthShift) 835 { 836 dstPicYuv = new TComPicYuv; 837 dstPicYuv->create( pPicYuv->getWidth(COMPONENT_Y), pPicYuv->getHeight(COMPONENT_Y), pPicYuv->getChromaFormat(), 1, 1, 0 ); 838 pPicYuv->copyToPic(dstPicYuv); 839 840 for(UInt comp=0; comp<dstPicYuv->getNumberValidComponents(); comp++) 841 { 842 const ComponentID compID=ComponentID(comp); 843 const ChannelType ch=toChannelType(compID); 844 #if !CLIP_TO_709_RANGE 845 const Pel minval = 0; 846 const Pel maxval = (1 << m_MSBExtendedBitDepth[ch]) - 1; 847 #else 848 const Bool b709Compliance=(-m_bitdepthShift[ch] < 0 && m_MSBExtendedBitDepth[ch] >= 8); /* ITU-R BT.709 compliant clipping for converting say 10b to 8b */ 849 const Pel minval = b709Compliance? (( 1 << (m_MSBExtendedBitDepth[ch] - 8)) ) : 0; 850 const Pel maxval = b709Compliance? ((0xff << (m_MSBExtendedBitDepth[ch] - 8)) -1) : (1 << m_MSBExtendedBitDepth[ch]) - 1; 851 #endif 852 853 scalePlane(dstPicYuv->getAddr(compID), dstPicYuv->getStride(compID), dstPicYuv->getWidth(compID), dstPicYuv->getHeight(compID), -m_bitdepthShift[ch], minval, maxval); 854 } 855 } 856 else 857 { 858 dstPicYuv = pPicYuv; 859 } 860 } 861 573 862 Bool retval = true; 574 575 if ((width==0)||(height==0)) 576 { 577 printf ("\nWarning: writing %d x %d luma sample output picture!", width, height); 578 } 579 580 if (m_bitDepthShiftY != 0 || m_bitDepthShiftC != 0) 581 { 582 dstPicTop = new TComPicYuv; 583 #if AUXILIARY_PICTURES 584 dstPicTop->create( pPicTop->getWidth(), pPicTop->getHeight(), pPicTop->getChromaFormat(), 1, 1, 0 ); 585 #else 586 dstPicTop->create( pPicTop->getWidth(), pPicTop->getHeight(), 1, 1, 0 ); 587 #endif 588 pPicTop->copyToPic(dstPicTop); 589 590 dstPicBottom = new TComPicYuv; 591 #if AUXILIARY_PICTURES 592 dstPicBottom->create( pPicBottom->getWidth(), pPicBottom->getHeight(), pPicBottom->getChromaFormat(), 1, 1, 0 ); 593 #else 594 dstPicBottom->create( pPicBottom->getWidth(), pPicBottom->getHeight(), 1, 1, 0 ); 595 #endif 596 pPicBottom->copyToPic(dstPicBottom); 597 598 Pel minvalY = 0; 599 Pel minvalC = 0; 600 Pel maxvalY = (1 << m_fileBitDepthY) - 1; 601 Pel maxvalC = (1 << m_fileBitDepthC) - 1; 602 #if CLIP_TO_709_RANGE 603 if (-m_bitDepthShiftY < 0 && m_fileBitDepthY >= 8) 604 { 605 /* ITU-R BT.709 compliant clipping for converting say 10b to 8b */ 606 minvalY = 1 << (m_fileBitDepthY - 8); 607 maxvalY = (0xff << (m_fileBitDepthY - 8)) -1; 608 } 609 if (-m_bitDepthShiftC < 0 && m_fileBitDepthC >= 8) 610 { 611 /* ITU-R BT.709 compliant clipping for converting say 10b to 8b */ 612 minvalC = 1 << (m_fileBitDepthC - 8); 613 maxvalC = (0xff << (m_fileBitDepthC - 8)) -1; 614 } 615 #endif 616 scalePlane(dstPicTop->getLumaAddr(), dstPicTop->getStride(), dstPicTop->getWidth(), dstPicTop->getHeight(), -m_bitDepthShiftY, minvalY, maxvalY); 617 scalePlane(dstPicTop->getCbAddr(), dstPicTop->getCStride(), dstPicTop->getWidth()>>1, dstPicTop->getHeight()>>1, -m_bitDepthShiftC, minvalC, maxvalC); 618 scalePlane(dstPicTop->getCrAddr(), dstPicTop->getCStride(), dstPicTop->getWidth()>>1, dstPicTop->getHeight()>>1, -m_bitDepthShiftC, minvalC, maxvalC); 619 620 scalePlane(dstPicBottom->getLumaAddr(), dstPicBottom->getStride(), dstPicBottom->getWidth(), dstPicBottom->getHeight(), -m_bitDepthShiftY, minvalY, maxvalY); 621 scalePlane(dstPicBottom->getCbAddr(), dstPicBottom->getCStride(), dstPicBottom->getWidth()>>1, dstPicBottom->getHeight()>>1, -m_bitDepthShiftC, minvalC, maxvalC); 622 scalePlane(dstPicBottom->getCrAddr(), dstPicBottom->getCStride(), dstPicBottom->getWidth()>>1, dstPicBottom->getHeight()>>1, -m_bitDepthShiftC, minvalC, maxvalC); 623 } 624 else 625 { 626 dstPicTop = pPicTop; 627 dstPicBottom = pPicBottom; 628 } 629 // location of upper left pel in a plane 630 Int planeOffset = 0; //cropLeft + cropTop * iStride; 631 //Write luma 632 if (! writeField(m_cHandle, dstPicTop->getLumaAddr() + planeOffset, dstPicBottom->getLumaAddr() + planeOffset, is16bit, iStride, width, height, isTff)) 633 { 634 retval=false; 635 goto exit; 636 } 637 638 width >>= 1; 639 height >>= 1; 640 iStride >>= 1; 641 cropLeft >>= 1; 642 cropRight >>= 1; 643 644 planeOffset = 0; // cropLeft + cropTop * iStride; 645 646 //Write chroma U 647 if (! writeField(m_cHandle, dstPicTop->getCbAddr() + planeOffset, dstPicBottom->getCbAddr() + planeOffset, is16bit, iStride, width, height, isTff)) 648 { 649 retval=false; 650 goto exit; 651 } 652 653 //Write chroma V 654 if (! writeField(m_cHandle, dstPicTop->getCrAddr() + planeOffset, dstPicBottom->getCrAddr() + planeOffset, is16bit, iStride, width, height, isTff)) 655 656 { 657 retval=false; 658 goto exit; 659 } 660 661 exit: 662 if (m_bitDepthShiftY != 0 || m_bitDepthShiftC != 0) 663 { 664 dstPicTop->destroy(); 665 delete dstPicTop; 666 dstPicBottom->destroy(); 667 delete dstPicBottom; 668 } 863 864 assert(dstPicYuvTop->getNumberValidComponents() == dstPicYuvBottom->getNumberValidComponents()); 865 assert(dstPicYuvTop->getChromaFormat() == dstPicYuvBottom->getChromaFormat() ); 866 assert(dstPicYuvTop->getWidth(COMPONENT_Y) == dstPicYuvBottom->getWidth(COMPONENT_Y) ); 867 assert(dstPicYuvTop->getHeight(COMPONENT_Y) == dstPicYuvBottom->getHeight(COMPONENT_Y) ); 868 assert(dstPicYuvTop->getStride(COMPONENT_Y) == dstPicYuvBottom->getStride(COMPONENT_Y) ); 869 870 for(UInt comp=0; retval && comp<dstPicYuvTop->getNumberValidComponents(); comp++) 871 { 872 const ComponentID compID = ComponentID(comp); 873 const ChannelType ch=toChannelType(compID); 874 875 assert(dstPicYuvTop->getComponentScaleX(compID) == dstPicYuvBottom->getComponentScaleX(compID)); 876 assert(dstPicYuvTop->getComponentScaleY(compID) == dstPicYuvBottom->getComponentScaleY(compID)); 877 assert(dstPicYuvTop->getStride (compID) == dstPicYuvBottom->getStride (compID)); 878 879 const UInt width444 = dstPicYuvTop->getWidth(COMPONENT_Y) - (confLeft + confRight); 880 const UInt height444 = dstPicYuvTop->getHeight(COMPONENT_Y) - (confTop + confBottom); 881 882 if ((width444 == 0) || (height444 == 0)) 883 { 884 printf ("\nWarning: writing %d x %d luma sample output picture!", width444, height444); 885 } 886 887 const UInt csx = dstPicYuvTop->getComponentScaleX(compID); 888 const UInt csy = dstPicYuvTop->getComponentScaleY(compID); 889 const Int planeOffset = (confLeft>>csx) + ( confTop>>csy) * dstPicYuvTop->getStride(compID); //offset is for entire frame - round up for top field and down for bottom field 890 891 if (! writeField(m_cHandle, 892 (dstPicYuvTop ->getAddr(compID) + planeOffset), 893 (dstPicYuvBottom->getAddr(compID) + planeOffset), 894 is16bit, 895 dstPicYuvTop->getStride(COMPONENT_Y), 896 width444, height444, compID, dstPicYuvTop->getChromaFormat(), format, m_fileBitdepth[ch], isTff)) 897 { 898 retval=false; 899 } 900 } 901 902 if (nonZeroBitDepthShift) 903 { 904 dstPicYuvTop->destroy(); 905 dstPicYuvBottom->destroy(); 906 delete dstPicYuvTop; 907 delete dstPicYuvBottom; 908 } 909 910 cPicYuvTopCSCd.destroy(); 911 cPicYuvBottomCSCd.destroy(); 912 669 913 return retval; 670 914 } 915 916 static Void 917 copyPlane(const TComPicYuv &src, const ComponentID srcPlane, TComPicYuv &dest, const ComponentID destPlane) 918 { 919 const UInt width=src.getWidth(srcPlane); 920 const UInt height=src.getHeight(srcPlane); 921 assert(dest.getWidth(destPlane) == width); 922 assert(dest.getHeight(destPlane) == height); 923 const Pel *pSrc=src.getAddr(srcPlane); 924 Pel *pDest=dest.getAddr(destPlane); 925 const UInt strideSrc=src.getStride(srcPlane); 926 const UInt strideDest=dest.getStride(destPlane); 927 for(UInt y=0; y<height; y++, pSrc+=strideSrc, pDest+=strideDest) 928 { 929 memcpy(pDest, pSrc, width*sizeof(Pel)); 930 } 931 } 932 933 // static member 934 Void TVideoIOYuv::ColourSpaceConvert(const TComPicYuv &src, TComPicYuv &dest, const InputColourSpaceConversion conversion, const Int bitDepths[MAX_NUM_CHANNEL_TYPE], Bool bIsForwards) 935 { 936 const ChromaFormat format=src.getChromaFormat(); 937 const UInt numValidComp=src.getNumberValidComponents(); 938 939 switch (conversion) 940 { 941 case IPCOLOURSPACE_YCbCrtoYYY: 942 if (format!=CHROMA_444) 943 { 944 // only 444 is handled. 945 assert(format==CHROMA_444); 946 exit(1); 947 } 948 949 { 950 for(UInt comp=0; comp<numValidComp; comp++) 951 copyPlane(src, ComponentID(bIsForwards?0:comp), dest, ComponentID(comp)); 952 } 953 break; 954 case IPCOLOURSPACE_YCbCrtoYCrCb: 955 { 956 for(UInt comp=0; comp<numValidComp; comp++) 957 copyPlane(src, ComponentID(comp), dest, ComponentID((numValidComp-comp)%numValidComp)); 958 } 959 break; 960 961 case IPCOLOURSPACE_RGBtoGBR: 962 { 963 if (format!=CHROMA_444) 964 { 965 // only 444 is handled. 966 assert(format==CHROMA_444); 967 exit(1); 968 } 969 970 // channel re-mapping 971 for(UInt comp=0; comp<numValidComp; comp++) 972 { 973 const ComponentID compIDsrc=ComponentID((comp+1)%numValidComp); 974 const ComponentID compIDdst=ComponentID(comp); 975 copyPlane(src, bIsForwards?compIDsrc:compIDdst, dest, bIsForwards?compIDdst:compIDsrc); 976 } 977 } 978 break; 979 980 case IPCOLOURSPACE_UNCHANGED: 981 default: 982 { 983 for(UInt comp=0; comp<numValidComp; comp++) 984 copyPlane(src, ComponentID(comp), dest, ComponentID(comp)); 985 } 986 break; 987 } 988 } -
branches/SHM-upgrade/source/Lib/TLibVideoIO/TVideoIOYuv.h
r595 r916 2 2 * License, included below. This software may be subject to other third party 3 3 * and contributor rights, including patent rights, and no such rights are 4 * granted under this license. 4 * granted under this license. 5 5 * 6 6 * Copyright (c) 2010-2014, ITU/ISO/IEC … … 56 56 private: 57 57 fstream m_cHandle; ///< file handle 58 Int m_fileBitDepthY; ///< bitdepth of input/output video file luma component 59 Int m_fileBitDepthC; ///< bitdepth of input/output video file chroma component 60 Int m_bitDepthShiftY; ///< number of bits to increase or decrease luma by before/after write/read 61 Int m_bitDepthShiftC; ///< number of bits to increase or decrease chroma by before/after write/read 62 58 Int m_fileBitdepth[MAX_NUM_CHANNEL_TYPE]; ///< bitdepth of input/output video file 59 Int m_MSBExtendedBitDepth[MAX_NUM_CHANNEL_TYPE]; ///< bitdepth after addition of MSBs (with value 0) 60 Int m_bitdepthShift[MAX_NUM_CHANNEL_TYPE]; ///< number of bits to increase or decrease image by before/after write/read 61 63 62 public: 64 63 TVideoIOYuv() {} 65 64 virtual ~TVideoIOYuv() {} 66 67 Void open ( Char* pchFile, Bool bWriteMode, Int fileBitDepthY, Int fileBitDepthC, Int internalBitDepthY, Int internalBitDepthC); ///< open or create file65 66 Void open ( Char* pchFile, Bool bWriteMode, const Int fileBitDepth[MAX_NUM_CHANNEL_TYPE], const Int MSBExtendedBitDepth[MAX_NUM_CHANNEL_TYPE], const Int internalBitDepth[MAX_NUM_CHANNEL_TYPE] ); ///< open or create file 68 67 Void close (); ///< close file 69 68 70 void skipFrames(UInt numFrames, UInt width, UInt height); 71 72 Bool read ( TComPicYuv* pPicYuv, Int aiPad[2] ); ///< read one YUV frame with padding parameter 73 Bool write( TComPicYuv* pPicYuv, Int confLeft=0, Int confRight=0, Int confTop=0, Int confBottom=0 ); 74 Bool write( TComPicYuv* pPicYuv, TComPicYuv* pPicYuv2, Int confLeft=0, Int confRight=0, Int confTop=0, Int confBottom=0, Bool isTff = false ); 75 69 Void skipFrames(UInt numFrames, UInt width, UInt height, ChromaFormat format); 70 71 // if fileFormat<NUM_CHROMA_FORMAT, the format of the file is that format specified, else it is the format of the TComPicYuv. 72 73 74 Bool read ( TComPicYuv* pPicYuv, TComPicYuv* pPicYuvTrueOrg, const InputColourSpaceConversion ipcsc, Int aiPad[2], ChromaFormat fileFormat=NUM_CHROMA_FORMAT ); ///< read one frame with padding parameter 75 Bool write ( TComPicYuv* pPicYuv, const InputColourSpaceConversion ipCSC, Int confLeft=0, Int confRight=0, Int confTop=0, Int confBottom=0, ChromaFormat fileFormat=NUM_CHROMA_FORMAT ); ///< write one YUV frame with padding parameter 76 Bool write ( TComPicYuv* pPicYuvTop, TComPicYuv* pPicYuvBottom, const InputColourSpaceConversion ipCSC, Int confLeft=0, Int confRight=0, Int confTop=0, Int confBottom=0, ChromaFormat fileFormat=NUM_CHROMA_FORMAT, Bool isTff=false); 77 static Void ColourSpaceConvert(const TComPicYuv &src, TComPicYuv &dest, const InputColourSpaceConversion conversion, const Int bitDepths[MAX_NUM_CHANNEL_TYPE], Bool bIsForwards); 78 76 79 Bool isEof (); ///< check for end-of-file 77 80 Bool isFail(); ///< check for failure 78 81 82 79 83 }; 80 84
Note: See TracChangeset for help on using the changeset viewer.