Ios6 使用UICollectionView创建书架

Ios6 使用UICollectionView创建书架,ios6,uicollectionview,uicollectionviewlayout,Ios6,Uicollectionview,Uicollectionviewlayout,我将在我的一个项目中创建一个书架。基本要求如下: 类似于iBooks书架 很好地支持两个方向 支持各种iOS设备(不同分辨率) 支持删除和插入项目 支持通过长按手势对项目进行重新排序 下拉第一行时显示隐藏的徽标 UICollectionView是我想到的第一个选项。它很容易支持网格单元。所以我在谷歌上搜索了一下,找到了一些非常有用的教程: 结果如下:(请忽略颜色不一致的问题,因为我选择的图形还不完美。) 我所做的: 通过创建从UICollectionFlowLayout继承的lxro

我将在我的一个项目中创建一个书架。基本要求如下:

  • 类似于iBooks书架
  • 很好地支持两个方向
  • 支持各种iOS设备(不同分辨率)
  • 支持删除和插入项目
  • 支持通过长按手势对项目进行重新排序
  • 下拉第一行时显示隐藏的徽标
UICollectionView是我想到的第一个选项。它很容易支持网格单元。所以我在谷歌上搜索了一下,找到了一些非常有用的教程:

结果如下:(请忽略颜色不一致的问题,因为我选择的图形还不完美。)

我所做的:

  • 通过创建从UICollectionFlowLayout继承的
    lxrorederableCollectionViewFlowLayout
    (用于重新排序)继承的类来创建自定义布局
  • 添加了用于显示徽标的装饰视图
  • 添加了用于显示书架的装饰视图
  • 但我遇到了一些问题:

    1。如果项目可以在一个屏幕上显示,我根本无法滚动

    然后我添加了以下代码,以使contentsize更大

    - (CGSize)collectionViewContentSize
    {
        return CGSizeMake(self.collectionView.bounds.size.width,      self.collectionView.bounds.size.height+100);
    }
    
    那我现在可以滚动了。在这里,我向下拉第一排:

    您可以看到徽标的装饰视图正在工作

    2。但当我把最后一行拉上来时,我遇到了第二组问题:

    您可以看到装饰视图未添加到绿框部分

    3。书架装饰视图的背景越来越暗。(请参阅

    4.当我重新排序项目时,书架栏有时会移动

    我在这里列出了一些重要的代码:

    - (void)prepareLayout
    {
        // call super so flow layout can do all the math for cells, headers, and footers
        [super prepareLayout];
        
        NSMutableDictionary *dictionary = [NSMutableDictionary dictionary];
        NSMutableDictionary *shelfLayoutInfo = [NSMutableDictionary dictionary];
        
        // decoration view - emblem
        NSIndexPath *indexPath = [NSIndexPath indexPathForItem:0 inSection:0];
        UICollectionViewLayoutAttributes *emblemAttributes =
            [UICollectionViewLayoutAttributes layoutAttributesForDecorationViewOfKind:[EmblemView kind]
                withIndexPath:indexPath];
        emblemAttributes.frame = [self frameForEmblem:YES];
        dictionary[[EmblemView kind]] = @{indexPath: emblemAttributes};
    
        // Calculate where shelves go in a vertical layout
        int sectionCount = [self.collectionView numberOfSections];
        
        CGFloat y = 0;
        CGFloat availableWidth = self.collectionViewContentSize.width - (self.sectionInset.left + self.sectionInset.right);
        int itemsAcross = floorf((availableWidth + self.minimumInteritemSpacing) / (self.itemSize.width + self.minimumInteritemSpacing));
        
        for (int section = 0; section < sectionCount; section++)
        {
            y += self.headerReferenceSize.height;
            //y += self.sectionInset.top;
            
            int itemCount = [self.collectionView numberOfItemsInSection:section];
            int rows = ceilf(itemCount/(float)itemsAcross)+1; // add 2 more empty row which doesn't have any data
            for (int row = 0; row < rows; row++)
            {
                indexPath = [NSIndexPath indexPathForItem:row inSection:section];
                shelfLayoutInfo[indexPath] = [NSValue valueWithCGRect:CGRectMake(0,y, self.collectionViewContentSize.width, self.itemSize.height + DECORATION_HEIGHT)];
                y += self.itemSize.height;
                
                if (row < rows - 1)
                    y += self.minimumLineSpacing;
            }
            
            y += self.sectionInset.bottom;
            y += self.footerReferenceSize.height;
        }
        
        dictionary[[ShelfView kind]] = shelfLayoutInfo;
        
        self.shelfLayoutInfo = dictionary;
    }
    
    
    - (NSArray *)layoutAttributesForElementsInRect:(CGRect)rect
    {
        NSArray *attributesArrayInRect = [super layoutAttributesForElementsInRect:rect];
        
        // cell layout info
        for (BookShelfLayoutAttributes *attribs in attributesArrayInRect)
        {
            
            attribs.zIndex = 1;
            CATransform3D t = CATransform3DIdentity;
            t = CATransform3DTranslate(t, 0, 0, 40);
            attribs.transform3D = CATransform3DRotate(t, 15 * M_PI / 180, 1, 0, 0);
        }
        
        // Add our decoration views (shelves)
        NSMutableDictionary* shelfDictionary = self.shelfLayoutInfo[[ShelfView kind]];
        NSMutableArray *newArray = [attributesArrayInRect mutableCopy];
        
        [shelfDictionary enumerateKeysAndObjectsUsingBlock:^(id key, NSValue* obj, BOOL *stop) {
            
            if (CGRectIntersectsRect([obj CGRectValue], rect))
            {
                UICollectionViewLayoutAttributes *attributes = [UICollectionViewLayoutAttributes layoutAttributesForDecorationViewOfKind:[ShelfView kind] withIndexPath:key];
                attributes.frame = [obj CGRectValue];
                
                NSLog(@"decorationView rect = %@",NSStringFromCGRect(attributes.frame));
                attributes.zIndex = 0;
                //attributes.alpha = 0.5; // screenshots
                [newArray addObject:attributes];
            }
        }];
        
        attributesArrayInRect = [NSArray arrayWithArray:newArray];
        
        NSMutableDictionary* emblemDictionary = self.shelfLayoutInfo[[EmblemView kind]];
        NSMutableArray *newArray2 = [attributesArrayInRect mutableCopy];
        [emblemDictionary enumerateKeysAndObjectsUsingBlock:^(NSIndexPath *indexPath, UICollectionViewLayoutAttributes *attributes, BOOL *innerStop) {
            if (CGRectIntersectsRect(rect, attributes.frame)) {
                [newArray2 addObject:attributes];
            }
        }];
        
        attributesArrayInRect = [NSArray arrayWithArray:newArray2];
        
        return attributesArrayInRect;
    }
    
    -(无效)准备就绪
    {
    //调用super,以便flow layout可以对单元格、页眉和页脚进行所有计算
    [超级准备];
    NSMutableDictionary*dictionary=[NSMutableDictionary];
    NSMutableDictionary*shelfLayoutInfo=[NSMutableDictionary];
    //装饰视图-徽章
    NSIndexPath*indexPath=[NSIndexPath indexPathForItem:0第0节:0];
    UICollectionViewLayoutAttribute*徽标属性=
    [UICollectionViewLayoutAttributes LayoutAttributes for生态理性视图种类:[徽章视图种类]
    withIndexPath:indexPath];
    徽标Attributes.frame=[self-frameForEmblem:是];
    字典[[徽标视图种类]]=@{indepath:徽标属性};
    //计算搁板在垂直布局中的位置
    int sectionCount=[self.collectionView numberOfSections];
    cgy=0;
    CGFloat availableWidth=self.collectionViewContentSize.width-(self.sectionInset.left+self.sectionInset.right);
    int itemscross=floorf((可用宽度+self.minimuminetemspaging)/(self.itemSize.width+self.minimuminetemspaging));
    对于(int section=0;section
    如果你有足够的耐心阅读这篇文章和公关,我将不胜感激