Skip to content
Snippets Groups Projects
Picture.cpp 65.7 KiB
Newer Older
  • Learn to ignore specific revisions
  •       int sum = 0;
          const TFilterCoeff* f = filterHor + frac * filterLength;
    
          for( int k = 0; k < filterLength; k++ )
          {
            int xInt = std::min<int>( std::max( 0, integer + k - filterLength / 2 + 1 ), orgWidth - 1 );
            sum += f[k] * org[xInt]; // postpone horizontal filtering gain removal after vertical filtering
          }
    
          *tmp = sum;
    
          tmp += scaledWidth;
          org += orgStride;
        }
      }
    
      Pel* dst = scaledSrc;
    
      for( int j = 0; j < scaledHeight; j++ )
      {
    
        int refPos = ( ( ( j << compScale.second ) - afterScaleTopOffset ) * scalingRatio.second + addY ) >> posShiftY;
    
        int integer = refPos >> numFracShift;
        int frac = refPos & numFracPositions;
    
        for( int i = 0; i < scaledWidth; i++ )
        {
    
    Philippe Bordes's avatar
    Philippe Bordes committed
    #if RPR_ENABLE && IF_12TAP
          uint64_t sum = 0;
    #else
    
    Philippe Bordes's avatar
    Philippe Bordes committed
    #endif
    
          int* tmp = buf + i;
          const TFilterCoeff* f = filterVer + frac * filterLength;
    
          for( int k = 0; k < filterLength; k++ )
          {
            int yInt = std::min<int>( std::max( 0, integer + k - filterLength / 2 + 1 ), orgHeight - 1 );
            sum += f[k] * tmp[yInt*scaledWidth];
          }
    
    
    Philippe Bordes's avatar
    Philippe Bordes committed
    #if RPR_ENABLE && IF_12TAP
          const uint64_t one = 1;
          int sumS = (int)((sum + (one << (log2Norm - 1))) >> log2Norm);
          dst[i] = std::min<int>(std::max(0, sumS), maxVal);
    #else
    
          dst[i] = std::min<int>( std::max( 0, ( sum + ( 1 << ( log2Norm - 1 ) ) ) >> log2Norm ), maxVal );
    
    Philippe Bordes's avatar
    Philippe Bordes committed
    #endif
    
    void Picture::rescalePicture( const std::pair<int, int> scalingRatio,
                                  const CPelUnitBuf& beforeScaling, const Window& scalingWindowBefore,
                                  const PelUnitBuf& afterScaling, const Window& scalingWindowAfter,
                                  const ChromaFormat chromaFormatIDC, const BitDepths& bitDepths, const bool useLumaFilter, const bool downsampling,
    
                                  const bool horCollocatedChromaFlag, const bool verCollocatedChromaFlag
    #if JVET_AB0082
                                , bool rescaleForDisplay, int upscaleFilterForDisplay
    #endif
    )
    
    {
      for( int comp = 0; comp < ::getNumberValidComponents( chromaFormatIDC ); comp++ )
      {
        ComponentID compID = ComponentID( comp );
        const CPelBuf& beforeScale = beforeScaling.get( compID );
        const PelBuf& afterScale = afterScaling.get( compID );
    
        sampleRateConv( scalingRatio, std::pair<int, int>( ::getComponentScaleX( compID, chromaFormatIDC ), ::getComponentScaleY( compID, chromaFormatIDC ) ),
    
                        beforeScale, scalingWindowBefore.getWindowLeftOffset() * SPS::getWinUnitX( chromaFormatIDC ), scalingWindowBefore.getWindowTopOffset() * SPS::getWinUnitY( chromaFormatIDC ),
                        afterScale, scalingWindowAfter.getWindowLeftOffset() * SPS::getWinUnitX( chromaFormatIDC ), scalingWindowAfter.getWindowTopOffset() * SPS::getWinUnitY( chromaFormatIDC ),
    
    Taoran Lu's avatar
    Taoran Lu committed
                        bitDepths.recon[toChannelType(compID)], downsampling || useLumaFilter ? true : isLuma( compID ), downsampling,
    
                        isLuma( compID ) ? 1 : horCollocatedChromaFlag, isLuma( compID ) ? 1 : verCollocatedChromaFlag
    #if JVET_AB0082
                      , rescaleForDisplay, upscaleFilterForDisplay
    #endif
        );
    
    void Picture::saveSubPicBorder(int POC, int subPicX0, int subPicY0, int subPicWidth, int subPicHeight)
    
    {
      // 1.1 set up margin for back up memory allocation
      int xMargin = margin >> getComponentScaleX(COMPONENT_Y, cs->area.chromaFormat);
      int yMargin = margin >> getComponentScaleY(COMPONENT_Y, cs->area.chromaFormat);
    
      // 1.2 measure the size of back up memory
      Area areaAboveBelow(0, 0, subPicWidth + 2 * xMargin, yMargin);
      Area areaLeftRight(0, 0, xMargin, subPicHeight);
      UnitArea unitAreaAboveBelow(cs->area.chromaFormat, areaAboveBelow);
      UnitArea unitAreaLeftRight(cs->area.chromaFormat, areaLeftRight);
    
      // 1.3 create back up memory
      m_bufSubPicAbove.create(unitAreaAboveBelow);
      m_bufSubPicBelow.create(unitAreaAboveBelow);
      m_bufSubPicLeft.create(unitAreaLeftRight);
      m_bufSubPicRight.create(unitAreaLeftRight);
    
      m_bufWrapSubPicAbove.create(unitAreaAboveBelow);
      m_bufWrapSubPicBelow.create(unitAreaAboveBelow);
    
      for (int comp = 0; comp < getNumberValidComponents(cs->area.chromaFormat); comp++)
    
      {
        ComponentID compID = ComponentID(comp);
    
        // 2.1 measure the margin for each component
        int xmargin = margin >> getComponentScaleX(compID, cs->area.chromaFormat);
        int ymargin = margin >> getComponentScaleY(compID, cs->area.chromaFormat);
    
        // 2.2 calculate the origin of the subpicture
    
        int left = subPicX0 >> getComponentScaleX(compID, cs->area.chromaFormat);
        int top = subPicY0 >> getComponentScaleY(compID, cs->area.chromaFormat);
    
    
        // 2.3 calculate the width/height of the subPic
    
        int width = subPicWidth >> getComponentScaleX(compID, cs->area.chromaFormat);
        int height = subPicHeight >> getComponentScaleY(compID, cs->area.chromaFormat);
    
        PelBuf s = M_BUFS(0, PIC_RECONSTRUCTION).get(compID);
    
        // 3.2.1 set back up buffer for left
        PelBuf dBufLeft   = m_bufSubPicLeft.getBuf(compID);
        Pel    *dstLeft   = dBufLeft.bufAt(0, 0);
    
        // 3.2.2 set back up buffer for right
        PelBuf dBufRight  = m_bufSubPicRight.getBuf(compID);
        Pel    *dstRight  = dBufRight.bufAt(0, 0);
    
        // 3.2.3 copy to recon picture to back up buffer
        Pel *srcLeft  = src - xmargin;
        Pel *srcRight = src + width;
        for (int y = 0; y < height; y++)
        {
          ::memcpy(dstLeft  + y *  dBufLeft.stride, srcLeft  + y * s.stride, sizeof(Pel) * xmargin);
          ::memcpy(dstRight + y * dBufRight.stride, srcRight + y * s.stride, sizeof(Pel) * xmargin);
    
        // 3.3.1 set back up buffer for above
    
        PelBuf dBufTop = m_bufSubPicAbove.getBuf(compID);
        Pel    *dstTop = dBufTop.bufAt(0, 0);
    
        PelBuf dBufBottom = m_bufSubPicBelow.getBuf(compID);
        Pel    *dstBottom = dBufBottom.bufAt(0, 0);
    
    
        // 3.3.3 copy to recon picture to back up buffer
    
        Pel *srcTop    = src - xmargin - ymargin * s.stride;
        Pel *srcBottom = src - xmargin +  height * s.stride;
    
        for (int y = 0; y < ymargin; y++)
    
          ::memcpy(dstTop    + y *    dBufTop.stride, srcTop    + y * s.stride, sizeof(Pel) * (2 * xmargin + width));
          ::memcpy(dstBottom + y * dBufBottom.stride, srcBottom + y * s.stride, sizeof(Pel) * (2 * xmargin + width));
    
    
        // back up recon wrap buffer
        if (cs->sps->getWrapAroundEnabledFlag())
        {
          PelBuf sWrap = M_BUFS(0, PIC_RECON_WRAP).get(compID);
          Pel *srcWrap = sWrap.bufAt(left, top);
    
          // 3.4.1 set back up buffer for above
          PelBuf dBufTopWrap = m_bufWrapSubPicAbove.getBuf(compID);
          Pel    *dstTopWrap = dBufTopWrap.bufAt(0, 0);
    
          // 3.4.2 set back up buffer for below
          PelBuf dBufBottomWrap = m_bufWrapSubPicBelow.getBuf(compID);
          Pel    *dstBottomWrap = dBufBottomWrap.bufAt(0, 0);
    
          // 3.4.3 copy recon wrap picture to back up buffer
          Pel *srcTopWrap    = srcWrap - xmargin - ymargin * sWrap.stride;
          Pel *srcBottomWrap = srcWrap - xmargin +  height * sWrap.stride;
          for (int y = 0; y < ymargin; y++)
          {
            ::memcpy(dstTopWrap    + y *    dBufTopWrap.stride, srcTopWrap    + y * sWrap.stride, sizeof(Pel) * (2 * xmargin + width));
            ::memcpy(dstBottomWrap + y * dBufBottomWrap.stride, srcBottomWrap + y * sWrap.stride, sizeof(Pel) * (2 * xmargin + width));
          }
        }
    
    void Picture::extendSubPicBorder(int POC, int subPicX0, int subPicY0, int subPicWidth, int subPicHeight)
    
      for (int comp = 0; comp < getNumberValidComponents(cs->area.chromaFormat); comp++)
    
      {
        ComponentID compID = ComponentID(comp);
    
        // 2.1 measure the margin for each component
        int xmargin = margin >> getComponentScaleX(compID, cs->area.chromaFormat);
        int ymargin = margin >> getComponentScaleY(compID, cs->area.chromaFormat);
    
        // 2.2 calculate the origin of the Subpicture
    
        int left = subPicX0 >> getComponentScaleX(compID, cs->area.chromaFormat);
        int top = subPicY0 >> getComponentScaleY(compID, cs->area.chromaFormat);
    
    
        // 2.3 calculate the width/height of the Subpicture
    
        int width = subPicWidth >> getComponentScaleX(compID, cs->area.chromaFormat);
        int height = subPicHeight >> getComponentScaleY(compID, cs->area.chromaFormat);
    
    Seungwook Hong's avatar
    Seungwook Hong committed
    #if JVET_Z0118_GDR
    
    Seungwook Hong's avatar
    Seungwook Hong committed
        int numPt = (cs->isGdrEnabled()) ? 2 : 1;    
        for (int i = 0; i < numPt; i++)
    
    Seungwook Hong's avatar
    Seungwook Hong committed
          PelBuf s = M_BUFS(0, PIC_RECONSTRUCTION+i).get(compID);
          Pel *src = s.bufAt(left, top);
    #else
          // 3.1 set reconstructed picture
          PelBuf s = M_BUFS(0, PIC_RECONSTRUCTION).get(compID);
          Pel *src = s.bufAt(left, top);
    #endif
    
          // 4.1 apply padding for left and right    
    
          Pel *dstLeft  = src - xmargin;
          Pel *dstRight = src + width;
          Pel *srcLeft  = src + 0;
          Pel *srcRight = src + width - 1;
    
          for (int y = 0; y < height; y++)
    
            for (int x = 0; x < xmargin; x++)
    
              dstLeft[x]  = *srcLeft;
              dstRight[x] = *srcRight;
    
            dstLeft += s.stride;
            dstRight += s.stride;
            srcLeft += s.stride;
            srcRight += s.stride;
    
    Seungwook Hong's avatar
    Seungwook Hong committed
          // 4.2 apply padding on bottom
          Pel *srcBottom = src + s.stride * (height - 1) - xmargin;
          Pel *dstBottom = srcBottom + s.stride;
          for (int y = 0; y < ymargin; y++)
          {
            ::memcpy(dstBottom, srcBottom, sizeof(Pel)*(2 * xmargin + width));
            dstBottom += s.stride;
          }
    
    Seungwook Hong's avatar
    Seungwook Hong committed
          // 4.3 apply padding for top
          // si is still (-marginX, SubpictureHeight-1)
          Pel *srcTop = src - xmargin;
          Pel *dstTop = srcTop - s.stride;
          // si is now (-marginX, 0)
          for (int y = 0; y < ymargin; y++)
          {
            ::memcpy(dstTop, srcTop, sizeof(Pel)*(2 * xmargin + width));
            dstTop -= s.stride;
          }
    #if JVET_Z0118_GDR
        } // for loop
    #endif 
    
    
        // Appy padding for recon wrap buffer
        if (cs->sps->getWrapAroundEnabledFlag())
        {
          // set recon wrap picture
          PelBuf sWrap = M_BUFS(0, PIC_RECON_WRAP).get(compID);
          Pel *srcWrap = sWrap.bufAt(left, top);
    
          // apply padding on bottom
          Pel *srcBottomWrap = srcWrap + sWrap.stride * (height - 1) - xmargin;
          Pel *dstBottomWrap = srcBottomWrap + sWrap.stride;
          for (int y = 0; y < ymargin; y++)
          {
            ::memcpy(dstBottomWrap, srcBottomWrap, sizeof(Pel)*(2 * xmargin + width));
            dstBottomWrap += sWrap.stride;
          }
    
          // apply padding for top
          // si is still (-marginX, SubpictureHeight-1)
          Pel *srcTopWrap = srcWrap - xmargin;
          Pel *dstTopWrap = srcTopWrap - sWrap.stride;
          // si is now (-marginX, 0)
          for (int y = 0; y < ymargin; y++)
          {
            ::memcpy(dstTopWrap, srcTopWrap, sizeof(Pel)*(2 * xmargin + width));
            dstTopWrap -= sWrap.stride;
          }
        }
    
    void Picture::restoreSubPicBorder(int POC, int subPicX0, int subPicY0, int subPicWidth, int subPicHeight)
    
      for (int comp = 0; comp < getNumberValidComponents(cs->area.chromaFormat); comp++)
    
      {
        ComponentID compID = ComponentID(comp);
    
        // 2.1 measure the margin for each component
        int xmargin = margin >> getComponentScaleX(compID, cs->area.chromaFormat);
        int ymargin = margin >> getComponentScaleY(compID, cs->area.chromaFormat);
    
        // 2.2 calculate the origin of the subpicture
    
        int left = subPicX0 >> getComponentScaleX(compID, cs->area.chromaFormat);
        int top = subPicY0 >> getComponentScaleY(compID, cs->area.chromaFormat);
    
    
        // 2.3 calculate the width/height of the subpicture
    
        int width = subPicWidth >> getComponentScaleX(compID, cs->area.chromaFormat);
        int height = subPicHeight >> getComponentScaleY(compID, cs->area.chromaFormat);
    
        PelBuf s = M_BUFS(0, PIC_RECONSTRUCTION).get(compID);
    
        // 4.2.1 copy from back up buffer to recon picture
        PelBuf dBufLeft = m_bufSubPicLeft.getBuf(compID);
        Pel    *dstLeft = dBufLeft.bufAt(0, 0);
    
        // 4.2.2 set back up buffer for right
        PelBuf dBufRight = m_bufSubPicRight.getBuf(compID);
        Pel    *dstRight = dBufRight.bufAt(0, 0);
    
        // 4.2.3 copy to recon picture to back up buffer
        Pel *srcLeft  = src - xmargin;
        Pel *srcRight = src + width;
    
        for (int y = 0; y < height; y++)
        {
          // the destination and source position is reversed on purpose
          ::memcpy(srcLeft  + y * s.stride,  dstLeft + y *  dBufLeft.stride, sizeof(Pel) * xmargin);
          ::memcpy(srcRight + y * s.stride, dstRight + y * dBufRight.stride, sizeof(Pel) * xmargin);
    
        // 4.3.1 set back up buffer for above
        PelBuf dBufTop = m_bufSubPicAbove.getBuf(compID);
        Pel    *dstTop = dBufTop.bufAt(0, 0);
    
        PelBuf dBufBottom = m_bufSubPicBelow.getBuf(compID);
        Pel    *dstBottom = dBufBottom.bufAt(0, 0);
    
    
        // 4.3.3 copy to recon picture to back up buffer
    
        Pel *srcTop = src - xmargin - ymargin * s.stride;
        Pel *srcBottom = src - xmargin + height * s.stride;
    
        for (int y = 0; y < ymargin; y++)
    
          ::memcpy(srcTop    + y * s.stride, dstTop    + y *    dBufTop.stride, sizeof(Pel) * (2 * xmargin + width));
          ::memcpy(srcBottom + y * s.stride, dstBottom + y * dBufBottom.stride, sizeof(Pel) * (2 * xmargin + width));
    
    
        // restore recon wrap buffer
        if (cs->sps->getWrapAroundEnabledFlag())
        {
          // set recon wrap picture
          PelBuf sWrap = M_BUFS(0, PIC_RECON_WRAP).get(compID);
          Pel *srcWrap = sWrap.bufAt(left, top);
    
          // set back up buffer for above
          PelBuf dBufTopWrap = m_bufWrapSubPicAbove.getBuf(compID);
          Pel    *dstTopWrap = dBufTopWrap.bufAt(0, 0);
    
          // set back up buffer for below
          PelBuf dBufBottomWrap = m_bufWrapSubPicBelow.getBuf(compID);
          Pel    *dstBottomWrap = dBufBottomWrap.bufAt(0, 0);
    
          // copy to recon wrap picture from back up buffer
          Pel *srcTopWrap = srcWrap - xmargin - ymargin * sWrap.stride;
          Pel *srcBottomWrap = srcWrap - xmargin + height * sWrap.stride;
    
          for (int y = 0; y < ymargin; y++)
          {
            ::memcpy(srcTopWrap    + y * sWrap.stride, dstTopWrap    + y *    dBufTopWrap.stride, sizeof(Pel) * (2 * xmargin + width));
            ::memcpy(srcBottomWrap + y * sWrap.stride, dstBottomWrap + y * dBufBottomWrap.stride, sizeof(Pel) * (2 * xmargin + width));
          }
        }
    
      }
    
      // 5.0 destroy the back up memory
      m_bufSubPicAbove.destroy();
      m_bufSubPicBelow.destroy();
      m_bufSubPicLeft.destroy();
      m_bufSubPicRight.destroy();
    
      m_bufWrapSubPicAbove.destroy();
      m_bufWrapSubPicBelow.destroy();
    
    void Picture::extendPicBorder( const PPS *pps )
    
        if( isWrapAroundEnabled( pps ) && ( !m_wrapAroundValid || m_wrapAroundOffset != pps->getWrapAroundOffset() ) )
        {
          extendWrapBorder( pps );
        }
    
    Seungwook Hong's avatar
    Seungwook Hong committed
    #if JVET_Z0118_GDR
    
    Seungwook Hong's avatar
    Seungwook Hong committed
      int numPt = (cs->isGdrEnabled()) ? PIC_RECONSTRUCTION_1 : PIC_RECONSTRUCTION_0;  
    
      for (int pt = (int) PIC_RECONSTRUCTION_0; pt <= (int) numPt; pt++)
    
    Seungwook Hong's avatar
    Seungwook Hong committed
      {
        for (int comp = 0; comp < getNumberValidComponents(cs->area.chromaFormat); comp++)
        {
          ComponentID compID = ComponentID(comp);
          PelBuf p = M_BUFS(0, (PictureType) pt).get(compID);
          Pel *piTxt = p.bufAt(0, 0);
          int xmargin = margin >> getComponentScaleX(compID, cs->area.chromaFormat);
          int ymargin = margin >> getComponentScaleY(compID, cs->area.chromaFormat);
    
          Pel*  pi = piTxt;
          // do left and right margins
          for (int y = 0; y < p.height; y++)
          {
            for (int x = 0; x < xmargin; x++)
            {
              pi[-xmargin + x] = pi[0];
              pi[p.width + x] = pi[p.width - 1];
            }
            pi += p.stride;
          }
    
          // pi is now the (0,height) (bottom left of image within bigger picture
          pi -= (p.stride + xmargin);
          // pi is now the (-marginX, height-1)
          for (int y = 0; y < ymargin; y++)
          {
            ::memcpy(pi + (y + 1)*p.stride, pi, sizeof(Pel)*(p.width + (xmargin << 1)));
          }
    
          // pi is still (-marginX, height-1)
          pi -= ((p.height - 1) * p.stride);
          // pi is now (-marginX, 0)
          for (int y = 0; y < ymargin; y++)
          {
            ::memcpy(pi - (y + 1)*p.stride, pi, sizeof(Pel)*(p.width + (xmargin << 1)));
          }
    
          // reference picture with horizontal wrapped boundary
          if (isWrapAroundEnabled(pps))
          {
            extendWrapBorder(pps);
          }
          else
          {
            m_wrapAroundValid = false;
            m_wrapAroundOffset = 0;
          }
        }
      }
    #else
    
      for(int comp=0; comp<getNumberValidComponents( cs->area.chromaFormat ); comp++)
      {
        ComponentID compID = ComponentID( comp );
        PelBuf p = M_BUFS( 0, PIC_RECONSTRUCTION ).get( compID );
        Pel *piTxt = p.bufAt(0,0);
        int xmargin = margin >> getComponentScaleX( compID, cs->area.chromaFormat );
        int ymargin = margin >> getComponentScaleY( compID, cs->area.chromaFormat );
    
        Pel*  pi = piTxt;
        // do left and right margins
    
        for (int y = 0; y < p.height; y++)
        {
          for (int x = 0; x < xmargin; x++)
    
    Philippe Hanhart's avatar
    Philippe Hanhart committed
          {
    
            pi[-xmargin + x] = pi[0];
            pi[p.width + x]  = pi[p.width - 1];
    
    Philippe Hanhart's avatar
    Philippe Hanhart committed
          }
    
    
        // pi is now the (0,height) (bottom left of image within bigger picture
        pi -= (p.stride + xmargin);
        // pi is now the (-marginX, height-1)
        for (int y = 0; y < ymargin; y++ )
        {
          ::memcpy( pi + (y+1)*p.stride, pi, sizeof(Pel)*(p.width + (xmargin << 1)));
        }
    
        // pi is still (-marginX, height-1)
        pi -= ((p.height-1) * p.stride);
        // pi is now (-marginX, 0)
        for (int y = 0; y < ymargin; y++ )
        {
          ::memcpy( pi - (y+1)*p.stride, pi, sizeof(Pel)*(p.width + (xmargin<<1)) );
        }
    
        // reference picture with horizontal wrapped boundary
    
        if ( isWrapAroundEnabled( pps ) )
        {
          extendWrapBorder( pps );
        }
        else
        {
          m_wrapAroundValid = false;
          m_wrapAroundOffset = 0;
        }
    
    Seungwook Hong's avatar
    Seungwook Hong committed
    #endif
    
    void Picture::extendWrapBorder( const PPS *pps )
    {
      for(int comp=0; comp<getNumberValidComponents( cs->area.chromaFormat ); comp++)
      {
        ComponentID compID = ComponentID( comp );
        PelBuf p = M_BUFS( 0, PIC_RECON_WRAP ).get( compID );
        p.copyFrom(M_BUFS( 0, PIC_RECONSTRUCTION ).get( compID ));
        Pel *piTxt = p.bufAt(0,0);
        int xmargin = margin >> getComponentScaleX( compID, cs->area.chromaFormat );
        int ymargin = margin >> getComponentScaleY( compID, cs->area.chromaFormat );
        Pel*  pi = piTxt;
        int xoffset = pps->getWrapAroundOffset() >> getComponentScaleX( compID, cs->area.chromaFormat );
        for (int y = 0; y < p.height; y++)
        {
          for (int x = 0; x < xmargin; x++ )
          {
            if( x < xoffset )
            {
              pi[ -x - 1 ] = pi[ -x - 1 + xoffset ];
              pi[  p.width + x ] = pi[ p.width + x - xoffset ];
            }
            else
            {
              pi[ -x - 1 ] = pi[ 0 ];
              pi[  p.width + x ] = pi[ p.width - 1 ];
            }
          }
          pi += p.stride;
        }
        pi -= (p.stride + xmargin);
        for (int y = 0; y < ymargin; y++ )
        {
          ::memcpy( pi + (y+1)*p.stride, pi, sizeof(Pel)*(p.width + (xmargin << 1)));
        }
        pi -= ((p.height-1) * p.stride);
        for (int y = 0; y < ymargin; y++ )
        {
          ::memcpy( pi - (y+1)*p.stride, pi, sizeof(Pel)*(p.width + (xmargin<<1)) );
        }
      }
      m_wrapAroundValid = true;
      m_wrapAroundOffset = pps->getWrapAroundOffset();
    }
    
    
    PelBuf Picture::getBuf( const ComponentID compID, const PictureType &type )
    {
    
    Vadim Seregin's avatar
    Vadim Seregin committed
    #if JVET_Z0118_GDR
    
    Seungwook Hong's avatar
    Seungwook Hong committed
      if (type == PIC_RECONSTRUCTION_0 || type == PIC_RECONSTRUCTION_1)
      {
        return M_BUFS(scheduler.getSplitPicId(), type).getBuf(compID);
      }
    #endif
    
    Vadim Seregin's avatar
    Vadim Seregin committed
      return M_BUFS( ( type == PIC_ORIGINAL || type == PIC_TRUE_ORIGINAL || type == PIC_FILTERED_ORIGINAL || type == PIC_ORIGINAL_INPUT || type == PIC_TRUE_ORIGINAL_INPUT || type == PIC_FILTERED_ORIGINAL_INPUT ) ? 0 : scheduler.getSplitPicId(), type ).getBuf( compID );
    
    }
    
    const CPelBuf Picture::getBuf( const ComponentID compID, const PictureType &type ) const
    {
    
    Vadim Seregin's avatar
    Vadim Seregin committed
    #if JVET_Z0118_GDR
    
    Seungwook Hong's avatar
    Seungwook Hong committed
      if (type == PIC_RECONSTRUCTION_0 || type == PIC_RECONSTRUCTION_1)
      {
        return M_BUFS(scheduler.getSplitPicId(), type).getBuf(compID);
      }
    #endif
    
    Vadim Seregin's avatar
    Vadim Seregin committed
      return M_BUFS( ( type == PIC_ORIGINAL || type == PIC_TRUE_ORIGINAL || type == PIC_FILTERED_ORIGINAL || type == PIC_ORIGINAL_INPUT || type == PIC_TRUE_ORIGINAL_INPUT || type == PIC_FILTERED_ORIGINAL_INPUT ) ? 0 : scheduler.getSplitPicId(), type ).getBuf( compID );
    
    }
    
    PelBuf Picture::getBuf( const CompArea &blk, const PictureType &type )
    {
      if( !blk.valid() )
      {
        return PelBuf();
      }
    
    #if ENABLE_SPLIT_PARALLELISM
    
      const int jId = ( type == PIC_ORIGINAL || type == PIC_TRUE_ORIGINAL || type == PIC_ORIGINAL_INPUT || type == PIC_TRUE_ORIGINAL_INPUT ) ? 0 : scheduler.getSplitPicId();
    
    #if JVET_AC0162_ALF_RESIDUAL_SAMPLES_INPUT
      if (type == PIC_PREDICTION)
    #else
    
      if( type == PIC_RESIDUAL || type == PIC_PREDICTION )
    
      {
        CompArea localBlk = blk;
        localBlk.x &= ( cs->pcv->maxCUWidthMask  >> getComponentScaleX( blk.compID, blk.chromaFormat ) );
        localBlk.y &= ( cs->pcv->maxCUHeightMask >> getComponentScaleY( blk.compID, blk.chromaFormat ) );
    
        return M_BUFS( jId, type ).getBuf( localBlk );
      }
    #endif
    
      return M_BUFS( jId, type ).getBuf( blk );
    }
    
    const CPelBuf Picture::getBuf( const CompArea &blk, const PictureType &type ) const
    {
      if( !blk.valid() )
      {
        return PelBuf();
      }
    
    #if ENABLE_SPLIT_PARALLELISM
    
      const int jId = ( type == PIC_ORIGINAL || type == PIC_TRUE_ORIGINAL ) ? 0 : scheduler.getSplitPicId();
    
    #if JVET_AC0162_ALF_RESIDUAL_SAMPLES_INPUT
      if (type == PIC_PREDICTION)
    #else
    
      if( type == PIC_RESIDUAL || type == PIC_PREDICTION )
    
      {
        CompArea localBlk = blk;
        localBlk.x &= ( cs->pcv->maxCUWidthMask  >> getComponentScaleX( blk.compID, blk.chromaFormat ) );
        localBlk.y &= ( cs->pcv->maxCUHeightMask >> getComponentScaleY( blk.compID, blk.chromaFormat ) );
    
        return M_BUFS( jId, type ).getBuf( localBlk );
      }
    #endif
    
      return M_BUFS( jId, type ).getBuf( blk );
    }
    
    PelUnitBuf Picture::getBuf( const UnitArea &unit, const PictureType &type )
    {
      if( chromaFormat == CHROMA_400 )
      {
        return PelUnitBuf( chromaFormat, getBuf( unit.Y(), type ) );
      }
      else
      {
        return PelUnitBuf( chromaFormat, getBuf( unit.Y(), type ), getBuf( unit.Cb(), type ), getBuf( unit.Cr(), type ) );
      }
    }
    
    const CPelUnitBuf Picture::getBuf( const UnitArea &unit, const PictureType &type ) const
    {
      if( chromaFormat == CHROMA_400 )
      {
        return CPelUnitBuf( chromaFormat, getBuf( unit.Y(), type ) );
      }
      else
      {
        return CPelUnitBuf( chromaFormat, getBuf( unit.Y(), type ), getBuf( unit.Cb(), type ), getBuf( unit.Cr(), type ) );
      }
    }
    
    Pel* Picture::getOrigin( const PictureType &type, const ComponentID compID ) const
    {
    #if ENABLE_SPLIT_PARALLELISM
    
      const int jId = ( type == PIC_ORIGINAL || type == PIC_TRUE_ORIGINAL ) ? 0 : scheduler.getSplitPicId();
    
    #endif
      return M_BUFS( jId, type ).getOrigin( compID );
    }
    
    
    void Picture::createSpliceIdx(int nums)
    {
      m_ctuNums = nums;
      m_spliceIdx = new int[m_ctuNums];
      memset(m_spliceIdx, 0, m_ctuNums * sizeof(int));
    }
    
    bool Picture::getSpliceFull()
    {
      int count = 0;
      for (int i = 0; i < m_ctuNums; i++)
      {
        if (m_spliceIdx[i] != 0)
    
    
    void Picture::addPictureToHashMapForInter()
    {
    
      int picWidth = slices[0]->getPPS()->getPicWidthInLumaSamples();
      int picHeight = slices[0]->getPPS()->getPicHeightInLumaSamples();
    
      uint32_t* blockHashValues[2][2];
    
      bool* bIsBlockSame[2][3];
    
      for (int i = 0; i < 2; i++)
      {
        for (int j = 0; j < 2; j++)
        {
    
          blockHashValues[i][j] = new uint32_t[picWidth*picHeight];
    
        }
    
        for (int j = 0; j < 3; j++)
        {
          bIsBlockSame[i][j] = new bool[picWidth*picHeight];
        }
      }
    
      m_hashMap.create(picWidth, picHeight);
    
      m_hashMap.generateBlock2x2HashValue(getOrigBuf(), picWidth, picHeight, slices[0]->getSPS()->getBitDepths(), blockHashValues[0], bIsBlockSame[0]);//2x2
      m_hashMap.generateBlockHashValue(picWidth, picHeight, 4, 4, blockHashValues[0], blockHashValues[1], bIsBlockSame[0], bIsBlockSame[1]);//4x4
      m_hashMap.addToHashMapByRowWithPrecalData(blockHashValues[1], bIsBlockSame[1][2], picWidth, picHeight, 4, 4);
    
      m_hashMap.generateBlockHashValue(picWidth, picHeight, 8, 8, blockHashValues[1], blockHashValues[0], bIsBlockSame[1], bIsBlockSame[0]);//8x8
      m_hashMap.addToHashMapByRowWithPrecalData(blockHashValues[0], bIsBlockSame[0][2], picWidth, picHeight, 8, 8);
    
      m_hashMap.generateBlockHashValue(picWidth, picHeight, 16, 16, blockHashValues[0], blockHashValues[1], bIsBlockSame[0], bIsBlockSame[1]);//16x16
      m_hashMap.addToHashMapByRowWithPrecalData(blockHashValues[1], bIsBlockSame[1][2], picWidth, picHeight, 16, 16);
    
      m_hashMap.generateBlockHashValue(picWidth, picHeight, 32, 32, blockHashValues[1], blockHashValues[0], bIsBlockSame[1], bIsBlockSame[0]);//32x32
      m_hashMap.addToHashMapByRowWithPrecalData(blockHashValues[0], bIsBlockSame[0][2], picWidth, picHeight, 32, 32);
    
      m_hashMap.generateBlockHashValue(picWidth, picHeight, 64, 64, blockHashValues[0], blockHashValues[1], bIsBlockSame[0], bIsBlockSame[1]);//64x64
      m_hashMap.addToHashMapByRowWithPrecalData(blockHashValues[1], bIsBlockSame[1][2], picWidth, picHeight, 64, 64);
    
      m_hashMap.setInitial();
    
      for (int i = 0; i < 2; i++)
      {
        for (int j = 0; j < 2; j++)
        {
          delete[] blockHashValues[i][j];
        }
    
        for (int j = 0; j < 3; j++)
        {
          delete[] bIsBlockSame[i][j];
        }
      }
    }
    
    Seungwook Hong's avatar
    Seungwook Hong committed
    
    #if JVET_Z0118_GDR
    void Picture::initCleanCurPicture()
    {   
    
    Seungwook Hong's avatar
    Seungwook Hong committed
      if (!cs->isGdrEnabled())
      {
        return;
      }
    
    
    Seungwook Hong's avatar
    Seungwook Hong committed
      const int picWidth = getPicWidthInLumaSamples();
      const int picHight = getPicHeightInLumaSamples();
      const int bitDepth = slices[0]->getSPS()->getBitDepth(CHANNEL_TYPE_LUMA);
      const Pel dirtyPelVal = 1 << (bitDepth - 1);
          
      UnitArea wholePictureArea = UnitArea(chromaFormat, Area(Position(0, 0), Size(picWidth, picHight)));
    
      getBuf(wholePictureArea, PIC_RECONSTRUCTION_0).fill(dirtyPelVal);
    
    Seungwook Hong's avatar
    Seungwook Hong committed
      getBuf(wholePictureArea, PIC_RECONSTRUCTION_1).fill(dirtyPelVal);
    
    Seungwook Hong's avatar
    Seungwook Hong committed
    
      cs->getMotionBuf(wholePictureArea, PIC_RECONSTRUCTION_0).fill(0);
      cs->getMotionBuf(wholePictureArea, PIC_RECONSTRUCTION_1).fill(0);
    
    Seungwook Hong's avatar
    Seungwook Hong committed
    #if JVET_W0123_TIMD_FUSION
      cs->getIpmBuf(wholePictureArea, PIC_RECONSTRUCTION_0).fill(0);
      cs->getIpmBuf(wholePictureArea, PIC_RECONSTRUCTION_1).fill(0);
    #endif
    }
    
    void Picture::copyCleanCurPicture()
    {
    
    Seungwook Hong's avatar
    Seungwook Hong committed
      if (!cs->isGdrEnabled())
      {
        return;
      }
    
    
      if (cs->isInGdrIntervalOrRecoveryPoc())
    
    Seungwook Hong's avatar
    Seungwook Hong committed
      {
        ChromaFormat chromaFormat = cs->sps->getChromaFormatIdc();
        int gdrEndX = cs->picHeader->getGdrEndX();
        int gdrEndY = cs->pps->getPicHeightInLumaSamples();
    
        UnitArea cleanArea = UnitArea(chromaFormat, Area(Position(0, 0), Size(gdrEndX, gdrEndY)));
    
        PelUnitBuf picBuf0 = getBuf(cleanArea, PIC_RECONSTRUCTION_0);
        PelUnitBuf picBuf1 = getBuf(cleanArea, PIC_RECONSTRUCTION_1);
    
        picBuf1.copyFrom(picBuf0);
      }
    }
    #endif