Wayne Rumble Wayne Rumble - 1 year ago 53
Swift Question

Value not persisting when using didSelectRowAtIndexPath

Hi im trying to pass a variable to another view controller from my tableview within the

didSelectRowAtIndexPath
func:

class MessagesViewController: UIViewController, UITableViewDelegate {

@IBOutlet var messagesTableView: UITableView!
@IBOutlet var invitesButton: UIButton!

var messagesTableViewDataSource: MessagesTableViewDatasource = MessagesTableViewDatasource()

override func viewDidLoad() {
super.viewDidLoad()

messagesTableView.dataSource = self.messagesTableViewDataSource

self.navigationController?.navigationBar.backgroundColor = UIColor.whiteColor()
self.navigationController?.navigationBar.translucent = false

let titleView = NavTitleView.init(frame: CGRect(x: 0, y: 0, width: 122, height: 32))
titleView.title = "Messages"
self.navigationItem.titleView = titleView

}

func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) {
let cell: MessageCell = tableView.cellForRowAtIndexPath(indexPath) as! MessageCell
let viewController = storyboard?.instantiateViewControllerWithIdentifier("ConversationViewController") as! ConversationViewController
viewController.conversationUUID = cell.conversationUUID
viewController.conversationProfileImage = cell.senderProfileImage
}

@IBAction func invitesButtonWasPressed() {
performSegueWithIdentifier("segueToInvites", sender: self)
}

override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
}
}


here is where the cell is built:

class MessagesTableViewDatasource: NSObject, UITableViewDataSource {

var messages: [InboundMessage] = []

func createMessagesArray(message: InboundMessage) {
self.messages.append(message)
}

func loadMessages() -> [InboundMessage] {
if self.messages.count > 0 {
return self.messages
} else {
InboundMessage.all { messages in
messages.forEach(self.createMessagesArray)
}
return self.messages
}
}

func createTableViewFooter(tableView: UITableView) {

let footer = UILabel(frame: CGRectMake(0, 0, tableView.bounds.size.width - 100, tableView.bounds.size.height))
footer.text = "You have no more messages."
footer.textAlignment = .Center
footer.textColor = UIColor(red: 0, green: 0, blue: 0, alpha: 0.25)
footer.font = Style.smallFont
footer.sizeToFit()
tableView.tableFooterView = footer
}

func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
loadMessages()
createTableViewFooter(tableView)

let dateFormatter = NSDateFormatter()
dateFormatter.dateStyle = NSDateFormatterStyle.ShortStyle
dateFormatter.timeStyle = NSDateFormatterStyle.ShortStyle

let cell: MessageCell = tableView.dequeueReusableCellWithIdentifier("MessageCell") as! MessageCell
cell.senderName.text = messages[indexPath.row].senderName
cell.senderText.text = messages[indexPath.row].senderText
cell.timeMessageReceived.text = dateFormatter.stringFromDate(messages[indexPath.row].timeAndDateMessageReceived)
cell.conversationUUID = messages[indexPath.row].conversationUUID

if (messages[indexPath.row].senderProfileImageName != nil) {
cell.senderProfileImage!.image = UIImage(named: messages[indexPath.row].senderProfileImageName)
}
if (messages[indexPath.row].hasBeenRead == false) {
cell.unOpenedImage!.image = UIImage(named: "RedDot")
}

return cell
}

func numberOfSectionsInTableView(tableView: UITableView) -> Int {
loadMessages()
if self.messages.count == 0 {
let noMessagesLabel = UILabel(frame: CGRectMake(0, 0, tableView.bounds.size.width, tableView.bounds.size.height))
noMessagesLabel.text = "You have no messages at the moment."
noMessagesLabel.textAlignment = .Center
noMessagesLabel.sizeToFit()
tableView.backgroundView = noMessagesLabel
tableView.separatorStyle = .None

return 0
}
return 1
}

func tableView(tableView: UITableView, heightForRowAtIndexPath indexPath: NSIndexPath) -> CGFloat {
return 50
}

func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return messages.count
}

}


but when i get back to my view controller the values are nil and i don't understand why. Here is the view controller it gets passed to:

class ConversationViewController: UIViewController {

@IBOutlet var conversationTableView: UITableView!

var conversationTableViewDataSource: ConversationTableViewDataSource = ConversationTableViewDataSource()
var conversationUUID: NSUUID!
var conversationProfileImage: UIImageView!

override func viewDidLoad() {
super.viewDidLoad()

conversationTableView.dataSource = self.conversationTableViewDataSource
conversationTableViewDataSource.conversationUUID = self.conversationUUID
conversationTableViewDataSource.conversationProfileImage = self.conversationProfileImage

self.navigationController?.navigationBar.backgroundColor = UIColor.whiteColor()
self.navigationController?.navigationBar.translucent = false

// let titleView = NavTitleView.init(frame: CGRect(x: 0, y: 0, width: 122, height: 32))
// titleView.title = "Messages"
// self.navigationItem.titleView = titleView

}

override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
}
}


I'm sure, i'm missing something simple but as i'm pretty new to all this i can't find it after much googling and was hoping for some insight.

Thanks

Answer Source

You need to use prepareForSegue method for that add prepareForSegue method inside your MessagesViewController

override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?) {
    if (segue.identifier == "segueToConversation") {
        let destVC = segue.destinationViewController as! ConversationViewController
        let cell = sender as! MessageCell
        destVC.conversationUUID = cell.conversationUUID
        destVC.passImage = cell.senderProfileImage.image
    }
}

Note: You cannot directly assign image to UIImageView object conversationProfileImage because it is not initialized yet, so that create on instance of UIImage in the ConversationViewController with name passImage as i written in answer an then use that image object in viewDidLoad to assign image to UIImageView.