Swift - просмотр UICollectionView по ячейке при сохранении горизонтального центрирования ячейки - PullRequest
0 голосов
/ 11 июля 2019

Во-первых, не уверен, что заголовок правильный или предлагает лучшее описание, но я не уверен, что еще использовать.

Итак, я работаю над приложением, и я попал в раздел, где я застрял при реализации пользовательского интерфейса. По сути, у меня есть VC (изображение ниже), которое может работать само по себе на основе информации, получаемой из файла JSON.

enter image description here

Дело в том, что мне нужно иметь карусельное меню в верхней части с неопределенным количеством ячеек (опять же, зависит от того, что я получаю из файла JSON). Я решил использовать для этого UICollectionView, и мне удалось реализовать основы без каких-либо проблем.

Но вот часть, где я застрял:

  1. Поскольку выбранная ячейка должна ВСЕГДА центрироваться, при выборе первой и последней ячеек между ячейкой и безопасной областью должно быть свободное пространство (см. Изображение выше).
  2. Свиток должен быть разбит на страницы. Обычно это не было бы проблемой, если бы ячейка UICollectionView имела ширину, почти равную ширине экрана, но требовалось бы иметь возможность прокручивать по одному элементу за раз (см. Второй экран выше).

Я пытался найти что-то похожее, но, возможно, я не ищу нужную вещь, потому что все, что я мог найти, это просмотр страницы UICollection по ячейкам, а не по экрану

Кроме того, если честно, я никогда не видел app / UICollectionView с таким поведением.

Я разместил части кода ниже, но это не очень поможет, поскольку это просто стандартные методы UICollectionView.

Есть предложения?

class PreSignupDataVC : UIViewController, UICollectionViewDelegateFlowLayout, UICollectionViewDataSource, UIPickerViewDelegate, UIPickerViewDataSource

@IBOutlet weak var cvQuestions: UICollectionView!

var questionCell : PreSignupDataQuestionCellVC!
var screenData : Array<PreSignupScreenData> = Array<PreSignupScreenData>()
var pvDataSource : [String] = []
var numberOfComponents : Int = 0
var numberOfRowsInComponent : Int = 0
var currentScreen : Int = 1
var selectedType : Int?
var selectedCell : Int = 0
var initialLastCellInsetPoint : CGFloat = 0.0

override func viewDidLoad()
{
    super.viewDidLoad()

    print("PreSignupDataVC > viewDidLoad")

    initialLastCellInsetPoint = (self.view.frame.width - 170)/2
    screenData = DataSingleton.sharedInstance.returnPreSignUpUIArray()[selectedType!].screenData
    numberOfComponents = screenData[currentScreen - 1].controls[0].numberOfComponents!
    numberOfRowsInComponent = screenData[currentScreen - 1].controls[0].controlDataSource.count
    pvDataSource = screenData[currentScreen - 1].controls[0].controlDataSource

    cvQuestions.register(UINib(nibName: "PreSignupDataQuestionCell",
                               bundle: nil),
                         forCellWithReuseIdentifier: "PreSignupDataQuestionCellVC")
}

func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int
{
    print("PreSignupDataVC > collectionView > numberOfItemsInSection")

    return screenData[currentScreen - 1].controls.count
}

func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell
{
    print("PreSignupDataVC > collectionView > cellForItemAt")

    questionCell = (cvQuestions.dequeueReusableCell(withReuseIdentifier: "PreSignupDataQuestionCellVC",
                                                    for: indexPath) as? PreSignupDataQuestionCellVC)!
    questionCell.vQuestionCellCellContainer.layer.cornerRadius = 8.0
    questionCell.lblQuestion.text = screenData[currentScreen - 1].controls[indexPath.row].cellTitle
    questionCell.ivQuestionCellImage.image = UIImage(named: screenData[currentScreen - 1].controls[indexPath.row].cellUnselectedIcon!)

    return questionCell
}

func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath)
{
    print("PreSignupDataVC > collectionView > didSelectItemAt")

    numberOfComponents = screenData[currentScreen - 1].controls[indexPath.row].numberOfComponents!
    numberOfRowsInComponent = screenData[currentScreen - 1].controls[indexPath.row].controlDataSource.count
    pvDataSource = screenData[currentScreen - 1].controls[indexPath.row].controlDataSource
    selectedCell = indexPath.row

    pvData.reloadAllComponents()
}

func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, insetForSectionAt section: Int) -> UIEdgeInsets
{
    print("PreSignupDataVC > collectionView > insetForSectionAt")

    return UIEdgeInsets(top: 0.0, left: initialLastCellInsetPoint, bottom: 00.0, right: initialLastCellInsetPoint)
}

1 Ответ

1 голос
/ 11 июля 2019

Вы можете использовать insetForSectionAtIndex, чтобы добавить интервал в первую и последнюю ячейку

UPDATE
Вы можете использовать вид прокрутки.
Во-первых: добавьте ведущий и конечный в представление прокрутки:
enter image description here

Второй: scrollView.clipsToBounds = false

В-третьих: добавить представление к представлению прокрутки

func setupScrollView() {
    DispatchQueue.main.async {
        self.scrollView.layoutIfNeeded() // in order to get correct frame

        let numberItem = 6
        let spaceBetweenView: CGFloat = 20
        let firstAndLastSpace: CGFloat = spaceBetweenView / 2            
        let width = self.scrollView.frame.size.width
        let height = self.scrollView.frame.size.height
        let numberOfView: CGFloat = CGFloat(numberItem)
        let scrollViewContentSizeWidth = numberOfView * width

        self.scrollView.contentSize = CGSize(width: scrollViewContentSizeWidth, height: height)

        for index in 0..<numberItem {
            let xCoordinate = (CGFloat(index) * (width)) + firstAndLastSpace
            let viewFrame = CGRect(x: xCoordinate, y: 0, width: width - spaceBetweenView, height: height)
            let view = UIView()
            view.backgroundColor = .red

            view.frame = viewFrame
            self.scrollView.addSubview(view)
        }
    }
}
...