क्या ffmpeg av libs एक सटीक पीटीएस वापस कर सकते हैं?

मैं एक एमपीईजी स्ट्रीम के साथ काम कर रहा हूं जो आईबीबीपी ... जीओपी अनुक्रम का उपयोग करता है। पहले 4 एवीपैकेट्स के लिए लौटाए गए (डीटीएस, पीटीएस) मान निम्नानुसार हैं: I = (0,3) बी = (1,1) बी = (2,2) पी = (3,6)

आई फ्रेम पर पीटीएस ऐसा लगता है कि यह कानूनी है, लेकिन फिर बी फ्रेम पर पीटीएस सही नहीं हो सकता है, क्योंकि बी फ्रेम को फ्रेम के पहले प्रदर्शित नहीं किया जाना चाहिए क्योंकि उनके पीटीएस मूल्य इंगित करते हैं। मैंने पैकेट को डीकोड करने और परिणामस्वरूप AVFrame में पीटीएस मान का उपयोग करने का भी प्रयास किया है, यह बताएं कि पीटीएस हमेशा शून्य पर सेट है।

क्या ffmpeg से सटीक पीटीएस प्राप्त करने का कोई तरीका है? यदि नहीं, तब ऑडियो सिंक करने का सबसे अच्छा तरीका क्या है?

0

2 उत्तर

मुझे लगता है कि मैंने आखिरकार यह पता लगाया कि http: //www.dranger में किए गए टिप्पणी के आधार पर क्या हो रहा है। com/ffmpeg/tutorial05.html :

ffmpeg पैकेट को पीछे रखता है ताकि avcodec_decode_video() द्वारा संसाधित किए जा रहे पैकेट का डीटीएस हमेशा वही हो फ्रेम के पीटीएस के रूप में लौटाएगा

अनुवाद: अगर मैं avcodec_decode_video() में एक पैकेट खिलाता हूं जिसमें 12 का पीटीएस है, avcodec_decode_video() उस पैकेट में निहित डीकोडेड फ्रेम नहीं लौटाएगा जब तक कि मैं इसे बाद में पैकेट न खिलाऊं जिसमें डीटीएस है 12. यदि पैकेट का पीटीएस अपने डीटीएस के समान है, तो दिया गया पैकेट फ्रेम के समान होता है। यदि पैकेट का पीटीएस इसके डीटीएस की तुलना में 2 फ्रेम बाद में है, तो avcodec_decode_video() फ्रेम में देरी करेगा और इसे तब तक वापस नहीं करेगा जब तक कि मैं 2 और पैकेट प्रदान नहीं करता।

इस व्यवहार के आधार पर, मुझे लगता है कि av_read_frame() शायद आईपीबीबी से आईबीबीपी तक पैकेट को फिर से व्यवस्थित कर रहा है ताकि avcodec_decode_video() को केवल 5 फ्रेम के बजाय 3 फ्रेम के लिए पी फ्रेम को बफर करना होगा। उदाहरण के लिए, इनपुट और अंतर के बीच का अंतर इस क्रम के साथ पी फ्रेम का उत्पादन 3 (6 - 3) है:

|                  I B B P B B P
|             DTS: 0 1 2 3 4 5 6
| decode() result:       I B B P

बनाम मानक क्रम के साथ 5 का अंतर (6 - 1):

|                  I P B B P B B
|             DTS: 0 1 2 3 4 5 6
| decode() result:       I B B P

but that is pure conjecture.

0
जोड़ा

मुझे काफी यकीन है कि आपको सटीक मूल्य मिल रहे हैं। यह आपकी मदद कर सकता है यदि आप एक एमपीईजी स्ट्रीम की तरह, एक स्ट्रीम के रूप में अच्छी तरह से मदद करते हैं। उस स्थिति में, आईबीबीपीबीबी से पहले जो आप देखते हैं वहां आम तौर पर एक और जीओपी होगा। शायद ऐसा कुछ (मूल प्रश्न के समान नोटेशन का उपयोग करके):

P(-3,-2)  B(-2,-1)  B(-1,0)

मूल रूप से I फ्रेम के बाद बी फ्रेम I फ्रेम और अंतिम पी फ्रेम पिछले GOP से आधारित होते हैं।

हालांकि यह वीडियो के साथ शुरू करने के लिए तार्किक अर्थ बनाता है:

Start GOP: IPBBPBBPBB...

बाद में यह होना चाहिए

Start GOP: IBBPBBPBBPBB
Start GOP: IBBPBBPBBPBB
Start GOP: IBB... 

याद रखें कि किसी भी बी फ्रेम को डीकोड करने से पहले और उसके बाद एक पूर्ण फ्रेम की आवश्यकता होती है। इसलिए बी फ्रेम की प्रत्येक जोड़ी को फ़ाइल में इससे पहले I या P फ्रेम से पहले प्रदर्शित किया जाना चाहिए।

एफएफएमपीईजी ने पहले जीओपी के "विशेष मामले" को भूल लिया होगा।

चूंकि पहले दो बी फ्रेमों में हेरफेर करने के लिए पहले फ्रेम नहीं है, इसलिए आप उन्हें सुरक्षित रूप से त्यागने में सक्षम होना चाहिए। बस अपने टाइमस्टैम्प को पहले I फ्रेम से बंद करें और ऑडियो स्ट्रीम को उसी राशि को समायोजित करें।

चाहे यह वास्तव में फ्रेम का नुकसान होगा, एफएफएमपीईजी के कार्यान्वयन पर निर्भर करेगा, लेकिन खराब स्थिति परिदृश्य यह है कि आप 83 मिलीसेकंड (24 फ्रेम/सेकेंड पर 2 फ्रेम) खो देते हैं।

0
जोड़ा
इस तरह के हैक (2 फ्रेम के नुकसान को स्वीकार करने) हैं ... हैकी :) शर्मनाक लेखन दस्तावेज इतना उबाऊ है कि लगभग कोई भी परेशान नहीं करता है।
जोड़ा लेखक Roman Starkov, स्रोत