CollectionView внутри TableView withOut StoryBoard/xib

collectionview
uicollectionviewcell
tableview
tableviewcell

#1

Мучаюсь уже не знаю сколько откладываю этот вопрос, помогите =(
Посмотрел уже десяток ютуб видео на всех языках, 90% верстают с xib и у всех всё так просто с этим вопросом, что я уже и не знаю…
Есть ViewController с TableView::grinning:

class TableVPlans: UIViewController {
var tableView: UITableView!

override func viewDidLoad() {
	super.viewDidLoad()
	setupView()
}
private func setupView() {
	view.backgroundColor = .white
	setupTableView()
}
private func setupTableView() {
	tableView = UITableView(frame: view.frame, style: .plain)
	tableView.translatesAutoresizingMaskIntoConstraints = false
	tableView.rowHeight = 100
	tableView.register(TableVPlansCell.self, forCellReuseIdentifier: TableVPlansCell.reuseID)
	view.addSubview(tableView)
	tableView.dataSource = self
	NSLayoutConstraint.activate([
		tableView.topAnchor.constraint(equalTo: view.layoutMarginsGuide.topAnchor, constant: 0),
		tableView.leadingAnchor.constraint(equalTo: view.leadingAnchor),
		tableView.trailingAnchor.constraint(equalTo: view.trailingAnchor),
		tableView.bottomAnchor.constraint(equalTo: view.bottomAnchor)
	])
}

}

extension TableVPlans: UITableViewDataSource {
func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {	5 }
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
	let cell = tableView.dequeueReusableCell(withIdentifier: TableVPlansCell.reuseID, for: indexPath) as! TableVPlansCell
	//cell = TableVPlansCell.init(style: .default, reuseIdentifier: TableVPlansCell.reuseID)
	cell.backgroundColor = .lightGray
		cell.collectionView.reloadData()
		return cell
	}}

Есть TableViewCell с CollectionView: :grinning:

    class TableVPlansCell: UITableViewCell {
	static let reuseID = "TableVPlansCell"

// MARK: - Private properties
private lazy var containerView: UIView = {
	let view = UIView()
	view.translatesAutoresizingMaskIntoConstraints = false
	view.clipsToBounds = true
	return view
}()
var collectionView: UICollectionView!
var levelAndNameLabel = UILabel()

override init(style: UITableViewCell.CellStyle, reuseIdentifier: String?) {
	super.init(style: style, reuseIdentifier: reuseIdentifier)
	setupCollectionView()
	setupSubviews()
	setupConstraints()
}
required init?(coder aDecoder: NSCoder) {
	super.init(coder: aDecoder)
}
func setupCell(level: Int) {
	levelAndNameLabel.text = "\(level)"
}
private func setupCollectionView() {
	let layout = UICollectionViewFlowLayout()
	layout.scrollDirection = .horizontal
	collectionView = UICollectionView(frame: .zero, collectionViewLayout: layout)
	collectionView.translatesAutoresizingMaskIntoConstraints = false
	collectionView.register(ColVInTVPlansCell.self, forCellWithReuseIdentifier: ColVInTVPlansCell.reuseID)
	collectionView.dataSource = self
	collectionView.delegate = self
	collectionView.autoresizingMask = [.flexibleWidth, .flexibleHeight]
	collectionView.backgroundColor = .brown
}
private func setupSubviews() {
	containerView.addSubview(levelAndNameLabel)
	containerView.addSubview(collectionView)
	contentView.addSubview(containerView)
}
private func setupConstraints() {
	NSLayoutConstraint.activate([
		containerView.leadingAnchor.constraint(equalTo: contentView.leadingAnchor, constant: 8),
		containerView.trailingAnchor.constraint(equalTo: contentView.trailingAnchor, constant: -8),
		containerView.topAnchor.constraint(equalTo: contentView.topAnchor),
		containerView.bottomAnchor.constraint(equalTo: contentView.bottomAnchor)
	])
	NSLayoutConstraint.activate([
		collectionView.topAnchor.constraint(equalTo: containerView.topAnchor, constant: 8),
		collectionView.leadingAnchor.constraint(equalTo: containerView.leadingAnchor, constant: 12),
		collectionView.trailingAnchor.constraint(equalTo: containerView.trailingAnchor, constant: -12),
		collectionView.heightAnchor.constraint(equalToConstant: containerView.frame.height/2)
	])
	NSLayoutConstraint.activate([
		levelAndNameLabel.topAnchor.constraint(equalTo: collectionView.bottomAnchor, constant: 8),
		levelAndNameLabel.leadingAnchor.constraint(equalTo: containerView.leadingAnchor, constant: 12),
		levelAndNameLabel.trailingAnchor.constraint(equalTo: containerView.trailingAnchor, constant: -12),
		levelAndNameLabel.bottomAnchor.constraint(equalTo: containerView.bottomAnchor)
	])
}}

extension TableVPlansCell: UICollectionViewDelegate, UICollectionViewDataSource, UICollectionViewDelegateFlowLayout {
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize {
	return CGSize(width: 50, height: 50)
}
func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath) {
	let colVCell = ColVInTVPlansCell()
	colVCell.setupCell(workoutNumber: 4)
}
func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
	print("===collectionView Cell numberOfItemsInSection===")
	return 5

}
func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
	let cell = collectionView.dequeueReusableCell(withReuseIdentifier: ColVInTVPlansCell.reuseID, for: indexPath) as! ColVInTVPlansCell
	cell.backgroundColor = .red
	return cell
}}

Ну и сама collectionViewCell:
class ColVInTVPlansCell: UICollectionViewCell {
static let reuseID = “ColVInTVPlansCell”

var workoutNumberLabel = UILabel()
override init(frame: CGRect) {
	super.init(frame: frame)
	backgroundColor = .blue
	setupSubviews()
	setupConstraints()
}
required init?(coder aDecoder: NSCoder) {
	super.init(coder: aDecoder)
}

func setupCell(workoutNumber: Int) {
	workoutNumberLabel.text = "\(workoutNumber))"
}

private func setupSubviews() {
	contentView.addSubview(workoutNumberLabel)
}

private func setupConstraints() {
	NSLayoutConstraint.activate([
		workoutNumberLabel.topAnchor.constraint(equalTo: contentView.topAnchor, constant: 8),
		workoutNumberLabel.leadingAnchor.constraint(equalTo: contentView.leadingAnchor, constant: 12),
		workoutNumberLabel.trailingAnchor.constraint(equalTo: contentView.trailingAnchor, constant: -12),
		workoutNumberLabel.bottomAnchor.constraint(equalTo: contentView.bottomAnchor),
		workoutNumberLabel.heightAnchor.constraint(equalToConstant: 50),
		workoutNumberLabel.widthAnchor.constraint(equalToConstant: 50)
	])
}

}
Сам код конечно намного сложнее, но я уже создал новый проект, чтобы потестить всё это, и я не понимаю, почему через code не работает, а через xib - работает, помогите (( Я уже 10 раз все переписывал, поэтому возможны какие то лишние вещи в коде


#2

В проекте уже около 10 экранов готовых, и tableView и CollectionView есть, и я просто не понимаю, что тут может не работать ((