0

メインビューにページスクロールビューがある壁紙アプリがあります。scrollview の各ページには 9 つの画像が表示されます。ビューがスクロールされると、次の 10 ページの画像をロードし、ロードした前の 10 ページの uiimages を nil に設定して、メモリ警告を回避します。

問題は、ビューがスクロールするときに、次の scrollview メソッドが呼び出されることです。dispatch_async に新しい画像をロードするブロック コードを配置しても、ビューがスクロールできるようになるまでに数秒の遅延があります。コードのセクション全体をディスパッチでコメントアウトすると、遅延はありません。

なぜこれが起こるのか誰かが何か考えているなら。教えてください。

どうもありがとうございました

- (void)scrollViewDidScroll:(UIScrollView *)scrollV
{
float fractionalPage = scrollView.contentOffset.x / self.view.frame.size.width;

if (curPageNum != lround(fractionalPage)) {

    curPageNum = lround(fractionalPage);        

    //display the page number
    pageNumLabel.text = [NSString stringWithFormat:@"%d",curPageNum+1];
    pageNumLabel.alpha = 1.0;
    [NSTimer scheduledTimerWithTimeInterval:1.0 target:self selector:@selector(dismissPageNum) userInfo:nil repeats:NO];


    //loading more pages with 9 image in each
    lastLoadedPageNum = MIN(lastLoadedPageNum + 10, numPages - 1);

    dispatch_queue_t getImages = dispatch_queue_create("Getting Images", nil);
    dispatch_async(getImages, ^{

        for (int i = curPageNum + 4 ; i <= lastLoadedPageNum ; i++) {

            int numPicsPerPage = 9;
            if (picsNames.count%9 && i == numPages-1) {

                numPicsPerPage = picsNames.count%9;
            }

            for (int j = 0 ; j < numPicsPerPage ; j++) {

                UIImage *image = [brain imageWith:[picsNames objectAtIndex:(i*9) + j]];

                dispatch_async(dispatch_get_main_queue(), ^{

                    //loading the image to imageview
                    UIImageView *imageView = (UIImageView *)[scrollView viewWithTag:IMAGE_VIEWS_TAG + (i*9) + j];
                    imageView.image = image;
                });
            }
        }
    });

    //setting old imageview images to nil to release memory
    int oldFirstLoadedPageNum = firtLoadedPageNum;
    firtLoadedPageNum = MAX(curPageNum - 4, 0);
    for (int i = oldFirstLoadedPageNum ; i < firtLoadedPageNum ; i++) {

        int numPicsPerPage = 9;
        if (picsNames.count%9 && i == numPages-1) {

            numPicsPerPage = picsNames.count%9;
        }

        for (int j = 0 ; j < numPicsPerPage ; j++) {

            UIImageView *imageView = (UIImageView *)[scrollView viewWithTag:IMAGE_VIEWS_TAG + (i*9) + j];
            imageView.image = nil;
            [((UIActivityIndicatorView *)[imageView viewWithTag:ACTIVITY_INDICATOR_TAG]) startAnimating];
        }            
    }
}
}

ブレインメソッドの画像とは:

-(UIImage *)imageWith:(NSString *)imageName
{
NSString *imagePath = [[NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) objectAtIndex:0] stringByAppendingPathComponent:imageName];
UIImage *image = [UIImage imageWithContentsOfFile:imagePath];

if (!image && [self connected]) {

    image = [UIImage imageWithData:[NSData dataWithContentsOfURL:[NSURL URLWithString:[NSString stringWithFormat:@"%@/%@", picsURL, imageName]]]];

    if (image) {

        [UIImagePNGRepresentation(image) writeToFile:imagePath atomically:YES];
    }

}

return image;
}
4

3 に答える 3

1

明らかに、コードがループしており、遅延が発生しています。ディスパッチは for ループ内にあるため、特定の反復の後にのみ呼び出されるため、ここでマルチスレッドを使用しても実際のメリットはないと思います。

于 2013-05-15T04:32:55.960 に答える
0

ほとんどの場合、ネストされた for ループを含むブロックの後のロジックが遅延を引き起こしています。それを別のメソッドに移動し、別のスレッドで実行します。

于 2013-05-14T20:21:08.893 に答える
0

マイク・ポラードが示唆したように、私は使用しました

dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_BACKGROUND,0) 

それ以外の

dispatch_queue_create("Getting Images", nil) 

そしてそれは問題を解決しました。

みんな、ありがとう。

于 2013-05-19T01:02:50.540 に答える