¿Diseño personalizado para la vista de colección en swift?

Tengo 7 celdas en una sección en una UICollectionView. He buscado por horas, pero todo lo que puedo encontrar es información sobre CollectionFlow y layouts personalizados con cientos de células. Todo lo que quiero es mostrar 7 celdas con diferentes identificadores en una vista de colección usando un layout como esta image:

introduzca la descripción de la imagen aquí

¿Cómo puedo lograr este layout?

Es posible con FlowLayout, pero debe personalizar los attributes FlowLayout.

Para diferentes tamaños de celdas, use este método:

-(CGSize)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout*)collectionViewLayout sizeForItemAtIndexPath:(NSIndexPath *)indexPath; 

Esa es mi solucion

 class HistoryLayout: UICollectionViewLayout { var delegate : HistoryLayoutDelegate? var yOffSet : CGFloat = 0 var xOffSetLand : CGFloat = 0 var xOffSetPort : CGFloat = 0 var portraitElements : [Int] = [] var portraintItemPositionIndex = PortraintItemPositionIndex.Left private var cache = [CGRect]() var contentHeight: CGFloat = 0.0 var contentWidth: CGFloat { let insets = collectionView!.contentInset return CGRectGetWidth(collectionView!.bounds) - (insets.left + insets.right) } override func collectionViewContentSize() -> CGSize { return CGSize(width: contentWidth, height: contentHeight) } override func layoutAttributesForElementsInRect(rect: CGRect) -> [UICollectionViewLayoutAttributes]? { var layoutAttributes = [UICollectionViewLayoutAttributes]() for item in 0 ..< collectionView!.numberOfItemsInSection(0) { let indexPath = NSIndexPath(forItem: item, inSection: 0) let attributes = UICollectionViewLayoutAttributes(forCellWithIndexPath: indexPath) attributes.frame = cache[item] if CGRectIntersectsRect(attributes.frame, rect) { layoutAttributes.append(attributes) } } //send index list of elements with portraint position if let _ = delegate { delegate?.elementsWithVerticalPosition(self.portraitElements) } return layoutAttributes } override func prepareLayout() { if cache.isEmpty { var gropCount = Int(collectionView!.numberOfItemsInSection(0) / 3) if collectionView!.numberOfItemsInSection(0) % 3 != 0 { gropCount++ } for index in 1...gropCount { self.improGroupByItem(index) contentHeight = ((contentWidth / 3) * 2) * CGFloat(index) } } } private func improGroupByItem(index : Int){ if index % 2 == 0 { xOffSetLand = contentWidth / 3 xOffSetPort = 0 self.portraintItemPositionIndex = .Right }else{ xOffSetLand = 0 xOffSetPort = (contentWidth / 3) * 2 self.portraintItemPositionIndex = .Left } if index > 1 { self.yOffSet += (contentWidth / 3) * 2 } addItemToStack(index) } func addItemToStack(gIndex : Int){ let columnWidth = self.contentWidth / 3 var frame : CGRect var dublicate = 0 for index in 1...3 { if index % portraintItemPositionIndex.rawValue == 0 { let width = columnWidth * 1 let height = columnWidth * 2 frame = CGRect(x: self.xOffSetPort, y: yOffSet, width: width, height: height) let indexOfPortElement = ((gIndex - 1)*3) + index - 1 portraitElements.append(indexOfPortElement) }else{ let width = columnWidth * 2 let height = columnWidth * 1 frame = CGRect(x: self.xOffSetLand, y: yOffSet + (height * CGFloat(dublicate)), width: width, height: height) dublicate++ } cache.append(frame) } } }