Example #1
0
void CBDDemuxer::ProcessClipLanguages()
{
  ASSERT(m_pTitle->clip_count >= 1 && m_pTitle->clips);
  for (uint32_t i = 0; i < m_pTitle->clip_count; ++i) {
    CLPI_CL *clpi = bd_get_clpi(m_pBD, i);
    ProcessClipInfo(clpi);
    bd_free_clpi(clpi);
  }
}
Example #2
0
void CBDDemuxer::ProcessBluRayMetadata()
{
  if (m_MVCPlayback) {
    HRESULT hr = OpenMVCExtensionDemuxer(m_NewClip);
    if (SUCCEEDED(hr)) {
      AVStream *mvcStream = m_MVCFormatContext->streams[m_MVCStreamIndex];

      // Create a fake stream and set the appropriate properties
      m_lavfDemuxer->AddMPEGTSStream(mvcStream->id, 0x20);
      AVStream *avstream = m_lavfDemuxer->GetAVStreamByPID(mvcStream->id);
      if (avstream) {
        avstream->codecpar->codec_id = AV_CODEC_ID_H264_MVC;
        avstream->codecpar->extradata = (BYTE *)av_mallocz(mvcStream->codecpar->extradata_size + FF_INPUT_BUFFER_PADDING_SIZE);
        avstream->codecpar->extradata_size = mvcStream->codecpar->extradata_size;
        memcpy(avstream->codecpar->extradata, mvcStream->codecpar->extradata, mvcStream->codecpar->extradata_size);
      }
    }
    else {
      m_MVCPlayback = FALSE;
    }
  }

  ASSERT(m_pTitle->clip_count >= 1 && m_pTitle->clips);
  int64_t max_clip_duration = 0;
  for (uint32_t i = 0; i < m_pTitle->clip_count; ++i) {
    int64_t clip_duration = (m_pTitle->clips[i].out_time - m_pTitle->clips[i].in_time);
    bool overwrite_info = false;
    if (clip_duration > max_clip_duration) {
      overwrite_info = true;
      max_clip_duration = clip_duration;
    }
    CLPI_CL *clpi = bd_get_clpi(m_pBD, i);
    ProcessClipInfo(clpi, overwrite_info);
    bd_free_clpi(clpi);
  }

  MPLS_PL * mpls = bd_get_title_mpls(m_pBD);
  if (mpls) {
    // Read the PG offsets and store them as metadata
    std::list<uint8_t> pg_sequences;
    for (int i = 0; i < mpls->play_item[0].stn.num_pg; i++) {
      AVStream *avstream = m_lavfDemuxer->GetAVStreamByPID(mpls->play_item[0].stn.pg[i].pid);
      if (mpls->play_item[0].stn.pg[i].ss_offset_sequence_id != 0xFF) {
        pg_sequences.push_back(mpls->play_item[0].stn.pg[i].ss_offset_sequence_id);
        if (avstream) {
          char offset[4];
          _itoa_s(mpls->play_item[0].stn.pg[i].ss_offset_sequence_id, offset, 10);
          av_dict_set(&avstream->metadata, "3d-plane", offset, 0);
        }
      }
    }

    // export the list of pg sequences
    if (pg_sequences.size() > 0)
    {
      // strip duplicate entries
      pg_sequences.sort();
      pg_sequences.unique();

      size_t size = pg_sequences.size() * 4;
      char *offsets = new char[size];
      offsets[0] = 0;

      // Append all offsets to the string
      for (auto it = pg_sequences.begin(); it != pg_sequences.end(); it++) {
        size_t len = strlen(offsets);
        if (len > 0) {
          offsets[len] = ',';
          len++;
        }
        _itoa_s(*it, offsets + len, size - len, 10);
      }

      av_dict_set(&m_lavfDemuxer->m_avFormat->metadata, "pg_offset_sequences", offsets, 0);
      delete[] offsets;
    }

    // Export a list of all IG offsets
    if (mpls->play_item[0].stn.num_ig > 0) {
      std::list<uint8_t> ig_sequences;
      for (int i = 0; i < mpls->play_item[0].stn.num_ig; i++) {
        if (mpls->play_item[0].stn.ig[i].ss_offset_sequence_id != 0xFF) {
          ig_sequences.push_back(mpls->play_item[0].stn.ig[i].ss_offset_sequence_id);
        }
      }

      if (ig_sequences.size() > 0) {
        // strip duplicate entries
        ig_sequences.unique();

        size_t size = ig_sequences.size() * 4;
        char *offsets = new char[size];
        offsets[0] = 0;

        // Append all offsets to the string
        for (auto it = ig_sequences.begin(); it != ig_sequences.end(); it++) {
          size_t len = strlen(offsets);
          if (len > 0) {
            offsets[len] = ',';
            len++;
          }
          _itoa_s(*it, offsets + len, size - len, 10);
        }

        av_dict_set(&m_lavfDemuxer->m_avFormat->metadata, "ig_offset_sequences", offsets, 0);
        delete[] offsets;
      }
    }
  }
}