プレビューのキャンセルに対応する 【QuickLook Plug-inの開発:実践的Macintoshプログラミング解説】

印刷用表示 |テキストサイズ 小 |中 |大 |

クイックルックプラグインの開発

実践的 Macintosh プログラミング解説

QuickLook Cover Flow.png

| HOME | 実際の機能を実装する | プレビューのキャンセルに対応する |

更新日 2011-10-02 | 作成日 2008-01-04

プレビューをキャンセルする機能を実装する

ループ内でキャンセルをチェック

 次にプレビューをキャンセルする機能を実装します。これは実現が簡単で、各ページのプレビュー画像を生成するループの中でキャンセルがあったかどうかを確認し、あればループを抜けるというコードを追加しただけです。

ポーリングを通じた取り消しLinkIconを参考にしました。

 サムネイル生成は短時間で終わると考えられるので、キャンセル機能の実装は割愛しました。

OSStatus GeneratePreviewForURL(
    void *thisInterface,
    QLPreviewRequestRef preview,
    CFURLRef url,
    CFStringRef contentTypeUTI,
    CFDictionaryRef options)
{
    int                 pictureWidth,pictureHeight;
    NSArray             *repeatingMotifs;
    NSKeyedUnarchiver   *unarchiver;

    if(![(NSString *)contentTypeUTI isEqualToString:RMGDocumentUTI])
        return noErr;
    if(![(NSURL *)url isFileURL])
        return noErr;

    NSAutoreleasePool   *pool = [[NSAutoreleasePool alloc] init];
    NSData  *data = [NSData dataWithContentsOfFile:[(NSURL *)url path]];

    unarchiver = [[NSKeyedUnarchiver alloc] initForReadingWithData:data];

    repeatingMotifs = [unarchiver decodeObjectForKey:RMGRepeatingMotifsKey];
    pictureWidth = [unarchiver decodeIntForKey:RMGPictureWidthKey];
    pictureHeight = [unarchiver decodeIntForKey:RMGPictureHeightKey];

    [unarchiver finishDecoding];
    [unarchiver release];

    CGRect  mediaBox = CGRectMake(0,0,pictureWidth,pictureHeight);
    NSRect  nsMediaBox = NSRectFromCGRect(mediaBox);
    RepeatingMotifView *renderingView =
        [[[RepeatingMotifView alloc] initWithFrame:nsMediaBox] autorelease];
    NSDictionary    *dict = [NSDictionary dictionaryWithObjectsAndKeys:
        [NSNumber numberWithInt:pictureWidth],kQLPreviewPropertyWidthKey,
        [NSNumber numberWithInt:pictureHeight],kQLPreviewPropertyHeightKey,
        nil];
    CGContextRef cgContext = QLPreviewRequestCreatePDFContext(
        preview,&mediaBox,NULL,(CFDictionaryRef)dict);
    if(cgContext)
    {
        NSGraphicsContext* context =
            [NSGraphicsContext
                graphicsContextWithGraphicsPort:(void *)cgContext
                                        flipped:YES];
        if(context)
        {
            [NSGraphicsContext saveGraphicsState];
            [NSGraphicsContext setCurrentContext:context];

            NSEnumerator    *enumerator = [repeatingMotifs objectEnumerator];
            RepeatingMotif  *repeatingMotif;

            while(repeatingMotif = [enumerator nextObject])
            {
                if(QLPreviewRequestIsCancelled(preview))
                    break;
                CGPDFContextBeginPage(cgContext,NULL);
                [renderingView setRepeatingMotif:repeatingMotif];
                [renderingView displayRectIgnoringOpacity:nsMediaBox
                                                inContext:context];
                CGPDFContextEndPage(cgContext);
            }

            [NSGraphicsContext restoreGraphicsState];
        }
        QLPreviewRequestFlushContext(preview,cgContext);
        CFRelease(cgContext);
    }

    [pool release];
    return noErr;
}