9

QTMovieView を使用していますが、次のログが表示され、その後に不明なセレクタ例外が発生することがあります。このプログラムには、ユーザーが QTMovieView のコントローラーを表示および非表示にするように設定するオプションがあります。プログラムがリンクしている SDK は 10.7 です。

「[StdMovieUISliderCell sliderType]: 認識できないセレクタがインスタンスに送信されました」

助けてくれてありがとう

4

4 に答える 4

6

これは、OS X Mountain Lion 10.8 で導入されたバグのようです (編集: OS X 10.7 に関するレポートもあります。以下のコメントを参照してください)。QTMovieView次のメジャー OS X リリースのいずれかで非推奨になると思います。最善の解決策は、AV Foundation (AVPlayerおよび対応するAVPlayerLayerクラス) に移行することです。Apple には、このフレームワークを使用したアセットの再生に関するドキュメントがあります。

つまり、AV Foundation に更新できない場合、またはAuto Layoutをオフにできない場合でも、不足しているメソッドを実行時にStdMovieUISliderCellクラスに動的に追加することで、この問題を修正できます。Objective C ランタイム ヘッダー ファイルを追加し、できるだけ早くメソッドを追加するよう+ (void)loadにしてください (たとえば、アプリケーション デリゲート内)。App Store の静的アナライザーが foo を拒否した理由から、rot13 のような単純なエンコーディングをクラス名に追加することも安全です。

// Make sure that we have the right headers.
#import <objc/runtime.h>

// The selectors should be recognized by class_addMethod().
@interface NSObject (SliderCellBugFix)

- (NSSliderType)sliderType;
- (NSInteger)numberOfTickMarks;

@end

// Add C implementations of missing methods that we’ll add
// to the StdMovieUISliderCell class later.
static NSSliderType SliderType(id self, SEL _cmd)
{
  return NSLinearSlider;
}

static NSInteger NumberOfTickMarks(id self, SEL _cmd)
{
  return 0;
}

// rot13, just to be extra safe.
static NSString *ResolveName(NSString *aName)
{
  const char *_string = [aName cStringUsingEncoding:NSASCIIStringEncoding];
  NSUInteger stringLength = [aName length];
  char newString[stringLength+1];

  NSUInteger x;
  for(x = 0; x < stringLength; x++)
  {
    unsigned int aCharacter = _string[x];

    if( 0x40 < aCharacter && aCharacter < 0x5B ) // A - Z
      newString[x] = (((aCharacter - 0x41) + 0x0D) % 0x1A) + 0x41;
    else if( 0x60 < aCharacter && aCharacter < 0x7B ) // a-z
      newString[x] = (((aCharacter - 0x61) + 0x0D) % 0x1A) + 0x61;
    else  // Not an alpha character
      newString[x] = aCharacter;
  }
  newString[x] = '\0';

  return [NSString stringWithCString:newString encoding:NSASCIIStringEncoding];
}

// Add both methods if they aren’t already there. This should makes this
// code safe, even if Apple decides to implement the methods later on.
+ (void)load
{
  Class MovieSliderCell = NSClassFromString(ResolveName(@"FgqZbivrHVFyvqrePryy"));

  if (!class_getInstanceMethod(MovieSliderCell, @selector(sliderType)))
  {
    const char *types = [[NSString stringWithFormat:@"%s%s%s",
      @encode(NSSliderType), @encode(id), @encode(SEL)] UTF8String];
    class_addMethod(MovieSliderCell, @selector(sliderType),
      (IMP)SliderType, types);
  }
  if (!class_getInstanceMethod(MovieSliderCell, @selector(numberOfTickMarks)))
  {
    const char *types = [[NSString stringWithFormat: @"%s%s%s",
      @encode(NSInteger), @encode(id), @encode(SEL)] UTF8String];
    class_addMethod(MovieSliderCell, @selector(numberOfTickMarks),
      (IMP)NumberOfTickMarks, types);
  }
}

両方の方法を実装する際に、次の 2 つの仮定を行いました。

  1. ムービー ビューには、円形スライダーではなく、線形スライダーのみを含めることができます。
  2. ムービー ビューには目盛りがありません。

後者は、ムービーにチャプターがある場合に問題になる可能性がありますが、チャプターは必要ないか使用しないため、どのように処理されるかわかりません。

于 2012-09-10T14:32:23.647 に答える
1

AutoLayout をオンにして setMovie: を使用しようとすると、同じ問題が発生しました。Xcode 4.4.1 への更新により、問題が修正されました。

于 2012-08-08T09:19:26.923 に答える
0

QtMovieView サブクラスに空の updateConstraintsForSubtreeIfNeeded メソッドを追加して、この問題を修正しました。

于 2014-04-03T09:16:53.053 に答える