Tengo un UICollectionViewController el uso de un UICollectionViewFlowLayout donde mi itemSize es el tamaño de la UICollectionView. Básicamente, esta es una línea de diseño de celdas, donde cada celda es de pantalla completa y se desplaza horizontalmente.

En mi UICollectionViewFlowLayout subclase, he reemplazado prepareLayout de la siguiente manera:

- (void)prepareLayout {
    self.itemSize = self.collectionView.frame.size;
    self.scrollDirection = UICollectionViewScrollDirectionHorizontal;
    self.collectionView.pagingEnabled = YES;
    self.minimumLineSpacing = 0.0;
    self.minimumInteritemSpacing = 0.0;
    self.sectionInset = UIEdgeInsetsZero;
    self.footerReferenceSize = CGSizeZero;
    self.headerReferenceSize = CGSizeZero;
}

La UICollectionViewController es muy básica devolución de 10 elementos en una sola sección. He incluido un proyecto de ejemplo en GitHub para más detalles.

Todo parece estar configurado correctamente. Se ve a la derecha en el simulador y en el dispositivo, pero, cuando la colección se muestra la vista, no se registra un error en la consola:

the behavior of the UICollectionViewFlowLayout is not defined because:
the item height must be less that the height of the UICollectionView minus the section insets top and bottom values.

Nota también de que la colección de controlador de vista en mi ejemplo es en un controlador de navegación y mientras que no parece particularmente necesario en el ejemplo, en mi mundo real caso necesito la vista de colección en un controlador de navegación.

InformationsquelleAutor Wes | 2014-05-11

8 Comentarios

  1. 69

    Hay una propiedad en UIViewControllerautomaticallyAdjustsScrollViewInsets–que por defecto YES. Esto significa que cuando un UIViewController tiene un UIScrollView en su punto de vista de la jerarquía–lo que es cierto de un UICollectionViewController–el contentInset la propiedad de que el desplazamiento de la vista se ajusta automáticamente a la cuenta de la pantalla consumido por la barra de estado, barra de navegación y la barra de herramientas o barra de pestañas.

    La documentación de la propiedad de los estados:

    automaticallyAdjustsScrollViewInsets

    Especifica si o no el controlador de vista debería ajustar automáticamente su desplazamiento de la vista de inserciones.

    @property(nonatomic, assign) BOOL automaticallyAdjustsScrollViewInsets

    Discusión

    Valor predeterminado es SÍ, lo que permite que el controlador de vista para ajustar su desplazamiento de la vista de inserciones en respuesta a los ámbitos de la pantalla consumido por la barra de estado, barra de navegación y la barra de herramientas o barra de pestañas. Establece en NO si desea administrar el desplazamiento de la vista de inserción de ajustes, tales como
    cuando hay más de un desplazamiento de la vista en la vista de jerarquía.

    La solución es establecer automaticallyAdjustsScrollViewInsets a NO en algún lugar de su UICollectionViewController subclase, como en viewDidLoad:

    - (void)viewDidLoad {
        [super viewDidLoad];
        self.automaticallyAdjustsScrollViewInsets = NO;
    }

    He puesto un proyecto de ejemplo en GitHub que ilustra este problema y la solución. Hay dos ramas: with_error y fixed_error. Aquí está una resumen de los cambios en GitHub.

    • niza – esta solucionado mi problema!
    • Yo lo hubiera hecho «hasta» dos veces si pudiera. También, tenga en cuenta que puede cambiar automaticallyAdjustsScrollViewInsets derecho en el Interface Builder.
    • maldita sea…gracias por eso. Yo realmente me estaba golpeando mi cabeza dura!
    • Mi colección punto de vista es uno de una vista de tabla de la célula subvistas, esta solución no funciona para mi situación.
    • No veo esa opción en el interface builder, estoy usando UICollectionView en UIViewController.
    • Seleccione su ViewController. En el Inspector es «Atributos» de la ficha donde usted encontrará en el «Controlador de Vista de la» sección
    • Gracias @nikans, sí me encontré con que, pero sigue el mismo problema.
    • Me enfrento a este problema sólo cuando me carga la imagen.

  2. 5

    Este problema solo se me ocurrió en 3x pantallas (es decir, el iPhone 6 Plus.) Como resultó, el diseño automático del motor no se realmente como infinito de valores de punto flotante (como .33333333), así que mi solución fue floor el retorno de la altura en sizeForItemAt:indexPath:.

    return CGSize(width: preferredWidth, height: floor(preferredHeight))
  3. 3

    iOS 11 de actualización: automaticallyAdjustsScrollViewInsets está en desuso en iOS 11.0.

    Apple recomienda el uso de UIScrollView‘s contentInsetAdjustmentBehavior método en su lugar. Que establece este valor a .never y el error ha desaparecido. También puede establecer esta propiedad en el Interface Builder.

    • He intentado esto y es un hack que hace que las células de animar en maneras divertidas mientras se desplaza. No recomiendo este. Consulte mi respuesta por lo que funcionó para mí.
    • Esto funcionó para mí. Gracias.
  4. 2

    Me encontré con este problema cuando gire el dispositivo de vertical a horizontal, de vuelta a la vertical. Quieres invalidar la collectionView‘s diseño sobre la rotación del dispositivo y antes de la llamada a super, así:

    - (void)viewWillTransitionToSize:(CGSize)size withTransitionCoordinator:(id<UIViewControllerTransitionCoordinator>)coordinator {
        //Causes collection view cells to be resized upon orientation change.
        //Important that this is called *before* call to super in order to prevent error from being logged to console.
        [self.collectionView.collectionViewLayout invalidateLayout];
    
        [super viewWillTransitionToSize:size withTransitionCoordinator:coordinator];
    
        //...
    }
  5. 1

    Como Maravilla, Yo tenía el mismo problema cuando rotación de paisaje (foto usando el ancho total) para el modo de retrato. Su propuesta fue el único que realmente me ayudó.

    Adjunto el código con la última Swift para su ObjC ejemplo … y como un bono, mi código para encontrar el centro de la célula de la vista de colección. Funciona muy agradable 😉

    /**
     -----------------------------------------------------------------------------------------------
    
     viewWillTransition()
    
     -----------------------------------------------------------------------------------------------
     */
    override func viewWillTransition(to size: CGSize, with coordinator: UIViewControllerTransitionCoordinator) {
    
        //find cell in the center of the screen and store it in a global variable
        let center = self.view.convert((self.collectionView!.center), to: self.collectionView)
    
        //get the indexPath for the cell in the center of the current screen
        if let index = collectionView!.indexPathForItem(at: center) {
    
            //store it in a class property
            self.indexPathOfCenterCell = index
        }
    
        //force recalculation of margins, borders, cell sizes etc.
        self.collectionView?.collectionViewLayout.invalidateLayout()
    
        //inform UIKit about it    
        super.viewWillTransition(to: size, with: coordinator)
    }
  6. 0

    Tuve problema similar.

    Después de la celda de carga, la cual está llena de ancho y algunos la altura de la pantalla. en alguna condición de que he cambiado la altura de la celda, a continuación, me estaba poniendo el mismo error

    para solucionar este

    He utilizado

       func updateHeightPerRatio(with image:UIImage) {
        let ratio = collectionView.bounds.width / image.size.width
        constHeightCollectionView .constant =  ceil(image.size.height * ratio)
        collectionView.reloadData()
        collectionView.performBatchUpdates({
            collectionView.layoutIfNeeded()
        }) { (completed) in
            self.collectionView.reloadData()
            self.layoutIfNeeded()
        }
    }

    Solución es volver a cargar los datos, a continuación, realizar batchupdate con la vista de colección re -calcular los marcos . después de que vuelva a cargar collectionview de nuevo se aplicará calculado marcos a la celda

    Y ahora no hay ningún registro para el problema por ahora.

    Espero que sea útil

  7. 0

    Esta manera, había trabajado para mí la perfección!.

    Sólo me resta la parte superior e inferior márgenes desde el punto de vista de la altura como se dijo en ese error.


    func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize {
    return CGSize(width: view.frame.width , height: view.frame.height - (view.safeAreaInsets.top + view.safeAreaInsets.bottom))
    }

    Espero te sirva de ayuda!

Dejar respuesta

Please enter your comment!
Please enter your name here