Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Using dispatch_async with self

I have run into this problem a few times while porting Objective-C code to Swift. Say I have the following code:

dispatch_async(dispatch_get_main_queue()) {     self.hostViewController?.view.addSubview(self.commandField) } 

This will result in an error, underlining the entire dispatch_async call, offering:

Could not find member 'addSubview' 

I assume this is an error that has not yet been properly implemented because if I put the addSubview call outside the dispatch_async block, the project builds fine. Initially I assumed it may have something to do with capturing self in the block. However, inserting [unowned self] in results in the same error, as does [weak self] in (after the appropriate ! unwrap operators have been inserted).

How can I get dispatch_async blocks to work in Swift that need to capture self?

like image 764
Ephemera Avatar asked Jun 07 '14 01:06

Ephemera


1 Answers

You should condition spinning off this action on the non-nullity, not test for it after you've already initiated it:

if let hostView = self.hostViewController?.view {     DispatchQueue.main.async {          hostView.addSubview(self.commandField)     } } else {     // handle nil hostView  } 

You should never unwrap an optional outside of an if let, or testing it first. Doing this should also resolve yer weak self issue.

like image 161
iluvcapra Avatar answered Oct 10 '22 18:10

iluvcapra