更新:我解决了我的主要问题,正确的图像没有加载,直到在collectionView上滚动。我在tableView:cellForRowAtIndexPath中添加了一个collectionView.reloadData()。我还做了一些更改来预加载序列数组,而不是在滚动表时构建它(tableView:cellForRowAtIndexPath)。
如果您有兴趣,请将更新添加到GitHub https://github.com/Druiced/OpenDeck
一旦我弄清楚如何在回车中放置动态值时防止应用程序崩溃,我会跟进(如果我将其设置为15,应用程序不会崩溃):
func collectionView(collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
return count(Array(sequenceArray[collectionView.tag])) / 2
}
原始邮寄: 请求一些指导。
本教程帮助我意识到这必须与我的DataSource / Delegate有关。作者使用addSubview构建单元格,而不是利用Xcode原型单元,这看起来很酷,所以我试图这样做。 http://ashfurrow.com/blog/putting-a-uicollectionview-in-a-uitableviewcell
欢迎任何批评我的方法或未遵循最佳做法的批评。
表中的每个单元格都有一个UICollectionView。集合视图中的每个单元格按照保存的"序列"的顺序显示图像。串。例如:" ADKDQDJDTD"链接到AD.png KD.png QD.png JD.png TD.png
我有两个问题似乎无法解决。
- 当数组长度驱动卡数时,numberOfItemsInSection变得很糟糕(返回handArray.count / 2)。如果我放置一个固定的数字,该应用程序将起作用,但不是很光滑。
- 当桌子第一次出现时,在我向上和向下滚动表格之前,不会显示正确的卡片。每个CollectionView的数据似乎都是交叉路径,因为当快速上下滚动时显示错误的卡片。
我几乎肯定这与我的数据源设置方式有关。
DeckTableViewController.swift
import UIKit
import Parse
var deviceID: String?
var noRefresh: Bool?
var sequenceArray: Array<Character>?
class DeckTableViewController: UITableViewController, UICollectionViewDelegate, UICollectionViewDataSource {
var handArray: Array<Character>!
var timeLineData:NSMutableArray = NSMutableArray()
override func viewDidLoad() {
super.viewDidLoad()
noRefresh = false
deviceId = UIDevice.currentDevice().identifierForVendor.UUIDString
}
override func viewDidAppear(animated: Bool) {
if noRefresh == false {
loadData()
noRefresh = true
}
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
override func numberOfSectionsInTableView(tableView: UITableView) -> Int {
return 1
}
override func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return timeLineData.count
}
override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
let cell:DeckTableViewCell = tableView.dequeueReusableCellWithIdentifier("Cell", forIndexPath: indexPath) as! DeckTableViewCell
let deck:PFObject = timeLineData.objectAtIndex(indexPath.row) as! PFObject
cell.collectionView.dataSource = self
cell.collectionView.delegate = self
let sequenceTemp = deck.objectForKey("Sequence") as! String
handArray = Array(sequenceTemp)
cell.sequenceId.setTitle(deck.objectId, forState: UIControlState.Normal)
cell.cardCountLabel.text = "\((count(sequenceTemp)/2))"
// Date to String Stuff
var dateFormatter = NSDateFormatter()
dateFormatter.dateFormat = "(MM-dd) hh:mm:ss"
cell.timeLabel.text = dateFormatter.stringFromDate(deck.updatedAt!)
let layout:UICollectionViewFlowLayout = UICollectionViewFlowLayout()
layout.itemSize = CGSizeMake(99, 140)
layout.scrollDirection = UICollectionViewScrollDirection.Horizontal
cell.collectionView.collectionViewLayout = layout
return cell
}
func collectionView(collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
return handArray.count / 2
}
func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell {
let cell:TableCollectionViewCell = collectionView.dequeueReusableCellWithReuseIdentifier("Cell", forIndexPath: indexPath) as! TableCollectionViewCell
var bcolor : UIColor = UIColor.orangeColor()
cell.layer.borderColor = bcolor.CGColor
cell.layer.borderWidth = 2
cell.layer.cornerRadius = 3
var firstLetter: Character!
var secondLetter: Character!
//Building card file names from Sequence data
if (indexPath.row * 2) + 1 <= handArray.count {
firstLetter = handArray[indexPath.row * 2]
secondLetter = handArray[indexPath.row * 2 + 1]
let imageNameString = "\(firstLetter)\(secondLetter).png"
let front = UIImage(named: imageNameString)
cell.ImageView.backgroundColor = UIColor.orangeColor()
cell.ImageView.image = front
}
return cell
}
DeckTableViewCell.swift
import UIKit
class DeckTableViewCell: UITableViewCell, UITextViewDelegate {
@IBOutlet var collectionView: UICollectionView!
@IBOutlet var sequenceId: UIButton!
@IBOutlet var timeLabel: UILabel!
@IBOutlet var cardCountLabel: UILabel!
override func awakeFromNib() {
super.awakeFromNib()
// Initialization code
}
override func setSelected(selected: Bool, animated: Bool) {
super.setSelected(selected, animated: animated)
}
}
TableCollectionViewCell.swift
导入UIKit
class TableCollectionViewCell: UICollectionViewCell {
@IBOutlet var ImageView: UIImageView!
}
对于这个例子,我将(返回handArray.count / 2)设置为10并加载3个序列。 顶部中心的数字表示每行的卡数。 请注意,CollectionView不会使用正确的卡进行更新,而是从其他CollectionView中获取数据。如果我在这个组合中添加更多序列,当向上和向下滚动时,正确的卡将填充有时,但不可预测。
感谢您的任何建议,我很高兴回到绘图板。干杯
答案 0 :(得分:7)
好的,让我们这样思考,您的DeckTableViewController
充当tableview的数据源,DeckTableViewCell
充当集合视图的数据源。
考虑到上述事情,我们创建了一个示例项目 我没有深入,我正在给你的例子,因为你经历了
让我们在ViewController
中使用单一视图应用创建示例项目
通过下面的代码,我获取了一个整数数组,其中包含一些值,表示在集合视图中显示多少个单元格。不要忘记添加tableview并设置其数据源并删除。
在我们编写控制器类之前,我们需要一些类,如自定义tableview cell
和自定义collection view cell
,我们首先创建它们
创建一个新文件,该文件是UICollectionViewCell
的子类,并将其命名为CustomCollectionViewCell
和xib
文件。
class CustomCollectionViewCell: UICollectionViewCell {
@IBOutlet weak var aLabel: UILabel! //to show the card number
@IBOutlet weak var imageView: UIImageView! //imageview i am setting it's background color
override init(frame: CGRect) {
super.init(frame: frame)
}
required init(coder aDecoder: NSCoder) {
super.init(coder: aDecoder)
}
override func awakeFromNib() {
super.awakeFromNib()
}
}
并为标签和图片视图创建一个出口,如上面的代码所示。
接下来,创建UITableViewCell
的新文件子类,并将其命名为CustomTableViewCell
xib file
。打开CustomTableViewCell.xib
文件并拖放collection view
并将其datasource
和delegate
设置为cell
而不是控制器。
并为集合视图创建一个插座,并将其命名为foldersCollectionView
。
传递以下代码
import UIKit
class CustomTableViewCell: UITableViewCell,UICollectionViewDataSource,UICollectionViewDelegate {
@IBOutlet weak var foldersCollectionView: UICollectionView!
override init(frame: CGRect) {
super.init(frame: frame)
}
required init(coder aDecoder: NSCoder) {
// fatalError("init(coder:) has not been implemented")
super.init(coder: aDecoder)
}
var folderCount:Int?
{
didSet(value)
{
}
}
override func awakeFromNib() {
super.awakeFromNib()
// Initialization code
//configure our collectionview
var aFlowLayout : UICollectionViewFlowLayout = UICollectionViewFlowLayout()
aFlowLayout.scrollDirection = UICollectionViewScrollDirection.Horizontal
aFlowLayout.itemSize = CGSizeMake(60.0, 90.0)
aFlowLayout.minimumLineSpacing = 10.0
aFlowLayout.minimumInteritemSpacing = 0.0
aFlowLayout.sectionInset = UIEdgeInsetsMake(2, 9, 0, 10)
foldersCollectionView.collectionViewLayout = aFlowLayout
foldersCollectionView.registerClass(CustomCollectionViewCell.self, forCellWithReuseIdentifier: "FOLDER_CELL")
var cNib:UINib? = UINib(nibName: "CustomCollectionViewCell", bundle: nil)
foldersCollectionView.registerNib(cNib, forCellWithReuseIdentifier: "FOLDER_CELL")
foldersCollectionView.frame = self.bounds
}
override func setSelected(selected: Bool, animated: Bool) {
super.setSelected(selected, animated: animated)
// Configure the view for the selected state
}
class func CreateCustomCell() -> CustomTableViewCell
{
var nibElements: Array = NSBundle.mainBundle().loadNibNamed("CustomTableViewCell", owner: self, options: nil)
var item: AnyObject?
for item in nibElements
{
if item is UITableViewCell
{
return item as CustomTableViewCell
}
}
return item as CustomTableViewCell
}
func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell {
var cell :CustomCollectionViewCell? = collectionView.dequeueReusableCellWithReuseIdentifier("FOLDER_CELL", forIndexPath: indexPath) as? CustomCollectionViewCell
//hear u can modify which image to be displayed in the collection view cell
cell?.aLabel.text = "Card:\(indexPath.row)"
return cell!
}
func collectionView(collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
return folderCount!
}
func numberOfSectionsInCollectionView(collectionView: UICollectionView) -> Int {
return 1
}
}
现在我们将代码发送到ViewController
类
现在刚刚通过以下代码
class ViewController: UIViewController,UITableViewDataSource,UITableViewDelegate {
var cardCountArray:[Int] = []
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a nib.
cardCountArray = [5,15,6,12,7,10]
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
func numberOfSectionsInTableView(tableView: UITableView) -> Int
{
return cardCountArray.count
}
func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int
{
return 1
}
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell
{
var cell:CustomTableViewCell? = tableView.dequeueReusableCellWithIdentifier("CELL") as? CustomTableViewCell;
if(cell == nil)
{
cell = CustomTableViewCell.CreateCustomCell()
}
cell?.folderCount = cardCountArray[indexPath.section]
cell?.foldersCollectionView.reloadData()
cell?.clipsToBounds = true
return cell!;
}
func tableView(tableView: UITableView, heightForRowAtIndexPath indexPath: NSIndexPath) -> CGFloat
{
return 100.0
}
func tableView(tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {
var headerView:UIView = UIView(frame: CGRectMake(0, 0, tableView.bounds.size.width, 70.0))
var labelTitle:UILabel = UILabel(frame: CGRectMake(0, 0, tableView.bounds.size.width, 35))
var descriptionTitle:UILabel = UILabel(frame: CGRectMake(0, 20,tableView.bounds.size.width , 30))
headerView.addSubview(labelTitle)
headerView.addSubview(descriptionTitle)
labelTitle.text = "TOTAL_CARDS in section:\(section)"
descriptionTitle.text = "This CARD_SECTION contains \(cardCountArray[section]) CARDS"
return headerView
}
func tableView(tableView: UITableView, heightForHeaderInSection section: Int) -> CGFloat {
return 50.0
}
}
结果将如下所示
如果有任何遗漏,请告诉我
您的评论我有一个数组,例如,[&#34; 2C3C4C5C6C7C&#34;,&#34; AD2D3D4D5D&#34;,&#34; 9H8H7H&#34;] < / p>
为此你需要进行以下修改
//for first row u get like this
//the string for the row is 2C3C4C5C6C7C
//stringForCell = "2C3C4C5C6C7C"
//2C
//3C
//4C
//5C
//6C
//7C
//for other cells u can get like below
//the string for the row is AD2D3D4D5D
//stringForCell = "AD2D3D4D5D"
//AD
//2D
//3D
//4D
//5D
//the string for the row is 9H8H7H
//stringForCell = "9H8H7H"
//9H
//8H
//7H
//in controller controller class define array of string
class ViewController: UIViewController,UITableViewDataSource,UITableViewDelegate {
var cardCountArray:[Int] = []
var stringArray : [String] = []
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a nib.
stringArray = ["2C3C4C5C6C7C", "AD2D3D4D5D", "9H8H7H"]
}
func numberOfSectionsInTableView(tableView: UITableView) -> Int
{
// return cardCountArray.count
return stringArray.count
}
func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell
{
var cell:CustomTableViewCell? = tableView.dequeueReusableCellWithIdentifier("CELL") as? CustomTableViewCell;
if(cell == nil)
{
cell = CustomTableViewCell.CreateCustomCell()
}
//cell?.folderCount = cardCountArray[indexPath.section]
cell?.stringForCell = stringArray[indexPath.section];
cell?.foldersCollectionView.reloadData()
cell?.clipsToBounds = true
return cell!;
}
//in custom tableview cell add a string variable
class CustomTableViewCell: UITableViewCell,UICollectionViewDataSource,UICollectionViewDelegate {
@IBOutlet weak var foldersCollectionView: UICollectionView!
var stringForCell:String = "" //add the string to hold the string
//rest of the code
func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell {
var cell :CustomCollectionViewCell? = collectionView.dequeueReusableCellWithReuseIdentifier("FOLDER_CELL", forIndexPath: indexPath) as? CustomCollectionViewCell
var str:NSString = stringForCell
var length = str.length
var totalLlength:Int = length/2
var indexStart = indexPath.row * (2);
var aRange = NSMakeRange(indexStart, 2)
var cardString:NSString = str.substringWithRange(aRange)
println(cardString)
cell?.aLabel.text = "Card: \(cardString)"
return cell!
}
func collectionView(collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
println("the string for the row is \(stringForCell)")
var str:NSString = stringForCell
var length:Int = str.length
return length / 2
//return folderCount!
}
func numberOfSectionsInCollectionView(collectionView: UICollectionView) -> Int {
return 1
}
我写了一篇关于how to add collection view inside custom table view cell的详细帖子。听到希望这给出了比这篇文章更详细的解释。