3

UITableViewCellあり、それらのいくつかにインタースティシャル画像をランダムに配置する必要があります。これは機能していますが、セルのキャッシュにより、画像はテーブルのさらに下に繰り返されています。セル 1、12、および 25 に画像を配置することを事前に決定したとします。これらのセルには画像が含まれますが、セル 1 の後、セル 4、8 などにも最初の画像が含まれる可能性があります。

cellForRowAtIndexPath画像を追加する基準を満たしていない場合は、キャッシュをクリアして画像を削除するように具体的に指示する必要があると思います。どうすればそれを行うことができますか?私はすでにelse、決定を下して画像を割り当てる if ステートメントを試しました。その で、の画像をにelse設定しようとしましたが、違いはありませんでした。UIImageViewnil

これらの画像が定期的にページを下ってスパムするのを防ぐために、キャッシュをクリアする他の方法はありますか? これが私のcellForRowAtIndexPath方法であり、現在その最後の行にある行elseは画像に影響を与えていないため、機能するものに置き換える必要があると思います!

- (UITableViewCell *) tableView: (UITableView *) tableView cellForRowAtIndexPath: (NSIndexPath *) indexPath
{
    // Make and allocate the cell if necessary.
    CustomCell *cell = [tableView dequeueReusableCellWithIdentifier: @"Cell"];
    if (cell == nil) {
        cell = [[CustomCell alloc] initWithStyle: UITableViewCellStyleValue1 reuseIdentifier: @"Cell"];
    }
    cell.lineLabel.text = [[self.fetchedResultsController objectAtIndexPath: indexPath] line];
    cell.actorLabel.text = [[self.fetchedResultsController objectAtIndexPath: indexPath] actor];
    [cell.lineLabel sizeToFitMultipleLines];

    // Get the size each label needs to be when constrained to set width and very long height (8000).
    CGSize labelSize = [cell.lineLabel.text sizeWithFont: cell.lineLabel.font constrainedToSize: CGSizeMake(265, 8000)];

    if ([[cellsToContainInterstitialImages allKeys] containsObject: [thisLine.lineID stringValue]]) {

        UIImageView *interstitialImage = [[UIImageView alloc] init];
        NSNumber *cellTypeNumber = [cellsToContainInterstitialImages valueForKey: [thisLine.lineID stringValue]];
        kInterstitialCellType cellType = [cellTypeNumber intValue];

        if (cellType == kInterstitialCellTypeFirst) {
            interstitialImage = [[UIImageView alloc] initWithImage: [UIImage imageNamed: @"man.png"]];
        }
        else if (cellType == kInterstitialCellTypeSecond) {
            interstitialImage = [[UIImageView alloc] initWithImage: [UIImage imageNamed: @"woman.png"]];
        }
        else {
            interstitialImage = [[UIImageView alloc] initWithImage: [UIImage imageNamed: @"child.png"]];
        }

        [interstitialImage setFrame: CGRectMake(10, cell.lineLabel.frame.size.height + cell.actorLabel.frame.size.height + 10, 150, 150)];
        [cell addSubview: interstitialImage];
    } else {
        UIImageView *interstitialImage = [[UIImageView alloc] init];
        [interstitialImage setImage: nil];
    }

    return cell;
}
4

3 に答える 3

1

コードのブランチは、画像をセルにelse追加しません。サブビューを追加するのではなく、画像を設定する必要があるように、セルのコンストラクターにinterstitialImageを追加するようにコードを変更する必要があります。UIImageViewcellForRowAtIndexPath

を に追加しUIImageViewCustomCell非公開にし、cellForRowAtIndexPathが使用するプロパティを提供します。

@interface CustomCell : UITableViewCell {
    UIImageView *_interstitialImage;
}
@property (nonatomic,readonly) UIImageView *interstitialImage;
@end

@implementation CustomCell 
-(id)initWithStyle:(UITableViewCellStyle) style reuseIdentifier:(NSString*)reuseId {
    if (self = [super initWithStyle:style reuseIdentifier:reuseId]) {
        _interstitialImage = [[UIImageView alloc] init];
         [_interstitialImage setImage: nil];
         [_interstitialImage setFrame: CGRectMake(10, cell.lineLabel.frame.size.height + cell.actorLabel.frame.size.height + 10, 150, 150)];
         [cell addSubview: _interstitialImage];
    }
    return self;
}
-(UIImageView*)interstitialImage {
    return _interstitialImage;
}
@end

これで、常に新しいものを割り当てる代わりにcellForRowAtIndexPath使用できます。これにより、画像を複数回追加することを回避できます。cell.interstitialImageUIImageView

if ([[cellsToContainInterstitialImages allKeys] containsObject: [thisLine.lineID stringValue]]) {
    NSNumber *cellTypeNumber = [cellsToContainInterstitialImages valueForKey: [thisLine.lineID stringValue]];
    kInterstitialCellType cellType = [cellTypeNumber intValue];

    if (cellType == kInterstitialCellTypeFirst) {
        [cell.interstitialImage setImage:[UIImage imageNamed: @"man.png"]];
    } else if (cellType == kInterstitialCellTypeSecond) {
        [cell.interstitialImage setImage:[UIImage imageNamed: @"woman.png"]];
    } else {
        [cell.interstitialImage setImage: [UIImage imageNamed: @"child.png"]];
    }
} else {
    [cell.interstitialImage setImage: nil];
}
于 2013-03-01T15:30:01.640 に答える
0

最も簡単な解決策は、プロトコルのtableView:willDisplayCell:forRowAtIndexPath:メソッドを使用することUITableViewDelegateです。この方法で細胞をきれいにします。

于 2013-03-01T15:32:40.953 に答える
0

問題は、そのif部分で画像ビューを追加することです。これは、セルが再利用されるにつれて、より多くの画像ビューを追加し続けることを意味します。

そのelse部分で、ダミーの画像ビューを作成し、その画像を に設定しますnil。このコードは、意図したことを実行しません-既存の画像をクリアします。

必要なことは、セルに 2 つ目の画像ビューを追加しないようにすることです。また、画像をクリアする必要がある場合は、新しい画像ビューを作成するのではなく、既存の画像ビューへの参照を取得します。

于 2013-03-01T15:34:15.273 に答える