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); } }
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; } } } }