2015-08-26 6 views
1

Мне несколько дней в программировании на iOS, поэтому, пожалуйста, несите меня. Я пытаюсь показать UICollectionView с матрицей некоторых изображений.UICollectionView не освежающий от dispatch_async

Проблема заключается в том, что изображения появляются, когда инициализация UICollectionView происходит изнутри dispatch_async. Инициализация отлично работает с viewDidLoad(). Оба вывода println можно наблюдать в консоли Xcode, поэтому фоновый процесс и последующие обновления пользовательского интерфейса на главном должны произойти.

я оставил другие функции, потому что, по-видимому, они не являются проблемой (INIT работает от viewDidLoad)

Использование Xcode 6.4. Target является iPhone 5, 8.4.1

Вот соответствующий код:

class MyCollectionViewController: UICollectionViewController, UICollectionViewDataSource, UICollectionViewDelegate { 

class MyClass { 
     var x: Int 
     var y: Int 
    var thumbnail: String 
     init(…) { 
     } 
    } 

    var list = [MyClass]() 

override func viewDidLoad() { 
     super.viewDidLoad() 

     // Register cell classes 
     // self.collectionView!.registerClass(UICollectionViewCell.self, forCellWithReuseIdentifier: reuseIdentifier) 

     // Do any additional setup after loading the view. 

    /* uncommenting this works fine 
     list.append(MyClass(x: 1000, y: 10, thumbnail: “img1.jpg”)) 
     list.append(MyClass(x: 1001, y: 11, thumbnail: “img2.jpg”)) 
     list.append(MyClass(x: 1002, y: 12, thumbnail: “img3.jpg”)) 
     list.append(MyClass(x: 1003, y: 13, thumbnail: “img4.jpg”)) 
     list.append(MyClass(x: 1004, y: 14, thumbnail: “img5.jpg”)) 
     list.append(MyClass(x: 1005, y: 15, thumbnail: “img6.jpg”)) 
    */ 

     dispatch_async(dispatch_get_global_queue(QOS_CLASS_USER_INITIATED, 0), { 
      println("This is run on the background queue") 

      dispatch_async(dispatch_get_main_queue(), {() -> Void in 
       println("This is run on the main queue, after the previous code in outer block") 

       // This code block below just shows a black screen 
     self.list.append(MyClass(x: 1000, y: 10, thumbnail: “img1.jpg”)) 
       self.list.append(MyClass(x: 1001, y: 11, thumbnail: “img2.jpg”)) 
       self.list.append(MyClass(x: 1002, y: 12, thumbnail: “img3.jpg”)) 
       self.list.append(MyClass(x: 1003, y: 13, thumbnail: “img4.jpg”)) 
       self.list.append(MyClass(x: 1004, y: 14, thumbnail: “img5.jpg”)) 
       self.list.append(MyClass(x: 1005, y: 15, thumbnail: “img6.jpg”)) 
      }) 
     }) 
… 
} 

UPDATE: Вот фиксированный код

class MyCollectionViewController: UICollectionViewController, UICollectionViewDataSource, UICollectionViewDelegate { 

class MyClass { 
     var x: Int 
     var y: Int 
    var thumbnail: String 
     init(…) { 
     } 
    } 

    var list = [MyClass]() 

override func viewDidLoad() { 
     super.viewDidLoad() 

     // Register cell classes 
     // self.collectionView!.registerClass(UICollectionViewCell.self, forCellWithReuseIdentifier: reuseIdentifier) 

     // Do any additional setup after loading the view. 
     dispatch_async(dispatch_get_global_queue(QOS_CLASS_USER_INITIATED, 0), { 
      println("This is run on the background queue") 

      dispatch_async(dispatch_get_main_queue(), {() -> Void in 
       println("This is run on the main queue, after the previous code in outer block") 

       self.list.append(MyClass(x: 1000, y: 10, thumbnail: “img1.jpg”)) 
       self.list.append(MyClass(x: 1001, y: 11, thumbnail: “img2.jpg”)) 
       self.list.append(MyClass(x: 1002, y: 12, thumbnail: “img3.jpg”)) 
       self.list.append(MyClass(x: 1003, y: 13, thumbnail: “img4.jpg”)) 
       self.list.append(MyClass(x: 1004, y: 14, thumbnail: “img5.jpg”)) 
       self.list.append(MyClass(x: 1005, y: 15, thumbnail: “img6.jpg”)) 

     // This statement solved the issue 
     self.collectionView?.reloadData() 
      }) 
     }) 
… 
} 
+0

Где вы его обновляете? – Sandeep

+0

Вызовите UICollectionViewObject (который будет CollectionView), чтобы перезагрузить его после добавления списка. collectionView.reloadData() – kandelvijaya

+0

@GeneratorOfOne Я не перезагрузил его нигде в коде. Это необходимо? –

ответ

2

UICollectionViewController или UITableViewController пытается вызвать источник данных когда вызывается viewDidLoad() и, следовательно, является синхронным. Если каким-то образом класс должен получать данные с сервера и делает это в хорошем асинхронном вызове, это означает, что данные будут поступать позже и после вызова методов источников данных для загрузки ячеек.

Теперь, чтобы перезагрузить данные после прибытия с сервера или асинхронной задачи, вызовите метод reloadData метода collectionView так.

dispatch_async(dispatch_get_global_queue(QOS_CLASS_USER_INITIATED, 0), { 
     println("This is run on the background queue") 

     dispatch_async(dispatch_get_main_queue(), {() -> Void in 
      println("This is run on the main queue, after the previous code in outer block") 

      // This code block below just shows a black screen 
    self.list.append(MyClass(x: 1000, y: 10, thumbnail: “img1.jpg”)) 
      self.list.append(MyClass(x: 1001, y: 11, thumbnail: “img2.jpg”)) 
      self.list.append(MyClass(x: 1002, y: 12, thumbnail: “img3.jpg”)) 
      self.list.append(MyClass(x: 1003, y: 13, thumbnail: “img4.jpg”)) 
      self.list.append(MyClass(x: 1004, y: 14, thumbnail: “img5.jpg”)) 
      self.list.append(MyClass(x: 1005, y: 15, thumbnail: “img6.jpg”)) 
     }) 
    self.collectionView.reloadData() //telling to reload the data once again 

    }) 

Подкласс UICollectionViewController получает крюк по умолчанию к розетке CollectionView, и мы использовали его.

Однако иногда то, что я делаю, помещает наблюдателя свойств в массив данных, а затем вызывает перезагрузку там.

var list = [MyClass](){ 
    didSet{ 
     //do some work like validation 
     collectionView.reloadData() 
    } 
} 

В любом случае, я надеюсь, что это поможет. Ура!

Смежные вопросы