¿Cómo volver a dibujar la rotation después de UICollectionViewCell no visible, list para cuando se produce la reutilización?

¿Cómo volver a dibujar UICollectionViewCell no visible listo para cuando se produce la reutilización?

Un enfoque en el que pensé era por el código en la function Layout Cell prepareForReuse, sin embargo, mientras que funciona no es óptimo, ya que provoca más re-dibujo y luego se requiere.

Antecedentes: Necesito desencadenar drawRect para las celdas después de un cambio de orientación que no son visibles actualmente, pero aparece para ser utilizado y no se han vuelto a dibujar, por lo que solo puedo ver que prepareForReuse sería apropiado. El problema es que estoy volviendo a dibujar todas las celdas de "reutilización", mientras que solo quiero volver a dibujar las que aparecieron inicialmente que se crearon durante la position de orientación anterior del dispositivo.

INFORMACIÓN ADICIONAL: actualmente estoy haciendo esto:

En ViewController:

 override func viewWillLayoutSubviews() { // Clear cached layout attributes (to ensure new positions are calculated) (self.cal.collectionViewLayout as! GCCalendarLayout).resetCache() self.cal.collectionViewLayout.invalidateLayout() // Trigger cells to networkingraw themselves (to get new widths etc) for cell in self.cal?.visibleCells() as! [GCCalendarCell] { cell.setNeedsDisplay() } // Not sure how to "setNeedsDisplay" on non visible cells here? } 

En class Layout Cell:

 override func prepareForReuse() { super.prepareForReuse() // Ensure "drawRect" is called (only way I could see to handle change in orientation self.setNeedsDisplay() // ISSUE: It does this also for subsequent "prepareForReuse" after all // non-visible cells have been re-used and re-drawn, so really // not optimal } 

Ejemplo de lo que sucede sin el código en prepareForReuse arriba. Instantánea tomada después de un cambio de orientación, y justo después de desplazarse un poco:

introduzca la descripción de la imagen aquí

Creo que ahora lo tengo aquí:

 import UIKit @IBDesignable class GCCalendarCell: UICollectionViewCell { var prevBounds : CGRect? override func layoutSubviews() { if let prevBounds = prevBounds { if !( (prevBounds.width == bounds.width) && (prevBounds.height == bounds.height) ) { self.setNeedsDisplay() } } } override func drawRect(rect: CGRect) { // Do Stuff self.prevBounds = self.bounds } } 

Se notó que esta comprobación no funcionaba en "prepareForReuse", ya que en este momento la celda no se había aplicado la rotation. Parece que funciona en "layoutSubviews" sin embargo.

Puede implementar algún tipo de comunicación entre las celdas y el controller de vista que contiene la vista de recostackción (protocolo y delegado o bloque pasado o incluso reference directa al VC). Luego, puede pedirle al controller de vista los cambios de rotation.

Es un poco desorderado, pero si tiene algún tipo de rastreo de rotation en el controller de vista, puede filtrar el setNeedsDisplay con una instrucción if simple.

Tenía celdas de actualización desafiadas similares que ya se mostraban y salían de la pantalla. Si bien el ciclo a través de las células ALLL puede no ser posible, refrescarse / hacer un bucle a través de las células no visibles. SI este es tu caso de uso, sigue leyendo. Pre – Advertencia: si está agregando este tipo de código, explique por qué lo está haciendo. Es un poco antiprotizante, pero puede ayudar a arreglar ese error y ayudar a enviar su aplicación, aunque agrega una complejidad innecesaria. No lo use en múltiples puntos en la aplicación.

Cualquier colecciónviewview que se desinicializa (fuera de la pantalla y se recicla) debe darse de baja automáticamente.

Patrón de notificación

 let kUpdateButtonBarCell = NSNotification.Name("kUpdateButtonBarCell") class Notificator { static func fireNotification(notificationName: NSNotification.Name) { NotificationCenter.default.post(name: notificationName, object: nil) } } extension UICollectionViewCell{ func listenForBackgroundChanges(){ NotificationCenter.default.removeObserver(self, name: kUpdateButtonBarCell, object: nil) NotificationCenter.default.addObserver(forName:kUpdateButtonBarCell, object: nil, queue: OperationQueue.main, using: { (note) in print( " contentView: ",self.contentView) }) } } override func collectionView(collectionView: UICollectionView!, cellForItemAtIndexPath indexPath: NSIndexPath!) -> UICollectionViewCell! { let cell = collectionView.dequeueReusableCellWithReuseIdentifier("die", forIndexPath: indexPath) as UICollectionViewCell cell.listenForBackgroundChanges() return cell } // Where appropriate broadcast notification to hook into all cells past and present Notificator.fireNotification(notificationName: kUpdateButtonBarCell) 

Patrón de delegado

Es posible simplificar esto … un ejercicio para el lector. simplemente no retenga las celdas (use un enlace débil); de lo contrario, tendrá pérdidas de memory.