在NSWindow上交换QTMovieView会导致闪烁



我想做的是:

  • 在一个屏幕上播放大师级的快速电影(prores或pjpg)(带音频)
  • 在另一个屏幕上与主屏幕同步播放另一部从属快速电影(prores或pjpg)
  • 当我向左或向右按时,循环播放不同的从属电影

这就是我所做的:

  • 为每个屏幕创建一个NSWindow
  • 创建一个QTMovies数组(实际上是每个屏幕的数组)
  • 创建一个QTMovieViews数组(实际上是每个屏幕的数组)
  • 正常播放主控QTMovie
  • 设置NSTimer以从主电影时间更新当前从属电影时间
  • 如果按键,请将窗口的内容视图切换到新的QTMovieView

我的完整代码在http://codepad.org/gDsJLPAy

这一切都很有效,但当我切换视频时,我会看到切换到的旧视频帧的单帧闪光。也就是说,如果我运行应用程序50帧并切换到SlaveVideo2,我会瞥见SlavVideo2帧0,然后它立即跳到SlaveVideo 2帧50,并照常进行。如果在20帧之后,我切换回SlaveVideo1,我瞥见了SlaveVideo2的第50帧,然后它跳到SlaveVideo 1的第70帧,并照常进行。

我想弄清楚这件事快疯了。我尝试过各种刷新、显示方法,但都无济于事。关于我该怎么解决这个问题,有什么想法吗?

附言:你可以在timerFireMethod中看到,如果我一直更新所有从属电影(而不仅仅是活动的),我就不会闪烁。显然,这不是一个解决方案,因为我一直在寻找大量的视频,这些视频太重了,没有必要!

附言:我试过在Quartz Composer中重新创建设置,但我遇到了完全相同的问题。

我在10.7.3

为了存档,我将在这里发布我的结论。

我找不到这个问题的直接解决办法。如果从属电影暂停,当我激活它的视图时——即使我稍微早一点开始播放电影——当它变得可见时,它首先显示旧帧。我找到的解决办法是让电影一直播放(这很糟糕)。

但是我发现了https://developer.apple.com/library/mac/#documentation/QuickTime/RM/MovieInternals/MTTimeSpace/B-第/2章MovieTimeandSpace.html

通过在主影片上调用GetMovieTimeBase,并将SetTimeBaseMasterTimeBase应用于从属影片,它允许这两部影片在后端同步播放,而无需手动保持同步。因此,整个同步代码可以简化为:

-(void)setLayerIndex:(int)i {
    // make sure target index is within bounds
    if(i<0) i=[[movies objectAtIndex:1] count]-1;
    else if(i>[[movies objectAtIndex:1] count]-1) i=0;
    // pause all slave views
    [[viewers objectAtIndex:1] makeObjectsPerformSelector:@selector(pause:) withObject:self];
    // save current index
    currentLayerIndex = i;
    // sync frame of new slave movie
    [[self currentSlaveMovie] setCurrentTime:[masterMovie currentTime]];
    // set windows view to QTView
    [[windows objectAtIndex:1] setContentView:[self currentSlaveView]];
    // set timebase of slave to timebase of master
    TimeBase masterTimeBase = GetMovieTimeBase([masterMovie quickTimeMovie]);
    TimeValue masterTimeScale = GetMovieTimeScale([masterMovie quickTimeMovie]);
    TimeRecord slaveZero;
    TimeValue slaveZeroTV = GetTimeBaseStartTime(masterTimeBase, masterTimeScale, &slaveZero); 
    SetMovieMasterTimeBase([[self currentSlaveMovie] quickTimeMovie], masterTimeBase, &slaveZero);    
    // play master movie
    [masterViewer play:self];
    // play slave movie
    [[self currentSlaveView] play:self];

}

相关内容

  • 没有找到相关文章

最新更新