我正在开发一个从磁盘读取媒体数据的应用程序,将其转换为适当的像素格式,然后将其传递给AVAssetWriter进行压缩并写入磁盘。我正在自己读取交错而不使用AVAssetReader。我的读者确保以串行方式呈现恰好一帧的视频数据和一帧的音频数据。我遇到的问题是,如果我没有将expectedMediaDataInRealTime属性设置为 YES ,则视频资产编写者将在完全30帧后始终为isReadyForMoreMediaData返回 NO 。如果我在30帧之前停止写入,它工作正常,输出文件有效。但是,如果我将expectedMediaDataInRealTime设置为YES,它可以在整个持续时间内完美运行,可以是几千帧。在expectMediaDataInRealTime设置为YES的情况下启动转码操作后,我在压缩一个非常长的视频的过程中观察了应用程序的内存使用情况,并且没有任何不合理的内存使用情况,也没有任何内存泄漏。并且得到的MOV文件似乎写得相当正常,例如正如人们所料,音频数据与视频数据交错。
那么,如果设置为YES没有明显的缺点,为什么我会将expectedMediaDataInRealTime设置为NO?这仅适用于使用Apple API读取数据(使用AVAssetReader)吗?文档说该属性控制“以理想的交错模式写入媒体数据以提高存储和回放效率”,但是当expectedMediaDataInRealTime设置为YES时,isReadyForMoreMediaData永远不会返回NO并且文件看起来写得很完美。因此,如果AVAssetWriter在此属性设置为YES时可以执行此操作,为什么设置为NO时无法执行此操作?来源完全一样。
除了“确保readyForMoreMediaData的值被恰当地计算”之外,这个属性究竟做了什么呢?(这对我来说绝对没有意义)?
答案 0 :(得分:0)
根据我的理解,将expectedMediaDataInRealTime设置为YES意味着编码器期待实时数据流馈送,例如相机等。在这种情况下,您将不断向编码器提供数据,isReadyForMoreMediaData将告诉您是否是可以将数据提供给编码器。如果isReadyForMoreMediaData为NO,则必须删除当前样本,并等待下一个样本到达并再次检查isReadyForMoreMediaData是否为YES。
另一方面,如果expectedMediaDataInRealTime为NO,则表示编码器没有采用实时源,而是采用离线数据流,例如AVAssetReader。在这种情况下,因为您可以自己控制流速,因此,当isReadyForMoreMediaData为NO时,您可以保持输入和编码器并等待isReadyForMoreMediaData变为YES(例如,使用无限循环来休眠并等待isReadyForMoreMediaData变化等。)。
我假设的目的是让内部机制尝试尽可能对齐交错音频和视频时间戳,因此,不会让播放器,解码器预先获取大量数据进行播放。它是数据源端数据完整性和回放端体验之间的折衷。虽然,我想你可以一直使用expectedMediaDataInRealTime为YES,但是如果isReadyForMoreMediaData == NO,最好丢弃早期喂食的样本。
答案 1 :(得分:0)
据我所知,这并不是完美的命名,而且有点令人困惑。
expectsMediaDataInRealTime
表示将帧推入AVAssetWriter
-无论是从相机还是从文件中将其推入30FPS都没有关系……这仅意味着要处理AVAssetWriter
框架。
如果将其设置为false
,则应拉框,并从源头索取。因此,它与realTime
无关,它是用来定义AVAssetWriter
是准备就绪时拉框架,还是被强制准备就绪并在有可用框架时对其进行处理。
此标志定义谁控制到达AVAssetWriter
的帧的时间。