How to pass data from collection view to table view class? - ios

Here I am having a model class in which from this I need to pass selected sku value from collection view to table view in another class can anyone help me how to implement this ?
Here is the code for didselect item at index path method
func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath) {
// Here you can check which Collection View is triggering the segue
if collectionView == firstCategory {
} else if collectionView == secondCategory {
// from other CollectionView
}else if collectionView == newCollection{
newPassedSku = newModel[indexPath.item].sku as? String
print(newPassedSku)
}else{
}
}
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "firstCategorySegue" {
_ = segue.destination as! ProductListViewController
}
else if segue.identifier == "secondCategorySegue" {
_ = segue.destination as! ProductListViewController
}else if segue.identifier == "newSegue"{
let detailsViewController = segue.destination as! ProductDetailsViewController
detailsViewController.index = newPassedSku
print(newPassedSku)
}
else {
_ = segue.destination as! ProductDetailsViewController
}
}

You need to make your segue directly from your collectionview controller to tableview controller, you are calling it from collectionview cell hence prepareforsegue is getting called first
func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath) {
if collectionView == newCollection{
newPassedSku = newModel[indexPath.item].sku as? String
self.performSegue(withIdentifier: "secondCategorySegue",
sender: nil)
}
}
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "newSegue"{
let detailsViewController = segue.destination as! ProductDetailsViewController
detailsViewController.index = newPassedSku
}
}

You have made direct segue from the Collection Cell instead of from ViewController. That is why the override func prepare(for segue: UIStoryboardSegue, sender: Any?) method is called before func collectionView(_ collectionView: UICollectionView, didSelectItemAt.
So you basically do need to make your segue from View Controller to the next View Controller.
Then you have to call the segue manually like:
self.prepare(for: "segueIdentifier", any: nil) inside func collectionView(_ collectionView: UICollectionView, didSelectIt method.
func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath) {
if collectionView == newCollection{
newPassedSku = newModel[indexPath.item].sku as? String
print(newPassedSku)
self.prepare(for: "segueIdentifier", sender: newPassedSku)
}
}
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "newSegue"{
guard index = sender as? String else {
return //do not segue if index is not valid
}
let detailsViewController = segue.destination as! ProductDetailsViewController
detailsViewController.index = index
print(newPassedSku)
}
}

Works perfectly when u need to pass data from model class
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "firstCategorySegue" {
_ = segue.destination as! ProductListViewController
}
else if segue.identifier == "secondCategorySegue" {
_ = segue.destination as! ProductListViewController
}else if segue.identifier == "newSegue"{
let detailsViewController = segue.destination as! ProductDetailsViewController
let indexPaths = self.newCollection.indexPathsForSelectedItems
let indexPath = indexPaths?[0]
let obj = newModel[(indexPath?.row)!]
detailsViewController.index = obj.sku as! String
print(obj.sku)
}
else {
_ = segue.destination as! ProductDetailsViewController
}
}

Related

Cannot perform segue from cell with indexPath

I am trying to perform a segue and pass data to detailViewController from my cell when tapped. I have tried with dummy data and I can pass them to detailScreen, however I would like to pass data that are related to cells.When I tapped a cell I get this error "Could not cast value of type ViewController to MovieCell" with line let selectedItem = ...
Thanks for your time and effort
Here is my code:
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "detailSegue"
{
let destination = segue.destination as! DetailViewController
let selectedItem = collectionView.indexPath(for: sender as! MovieCell)!
let character = characters[selectedItem.item]
destination.detailName = character.name
destination.detailGender = character.gender
destination.detailSpecies = character.species
destination.detailStatus = character.status
}
}
override func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath) {
performSegue(withIdentifier: "detailSegue", sender: self)
}
try use:
collectionView.indexPathsForSelectedItems.first
instead
collectionView.indexPath(for: sender as! MovieCell)!
Also I wanna recommend for you my library for such situations: Link

IOS/Swift: Pass Object in tableview to detail view controller

I am trying to grab an object from a tableview and pass it to a detail view, something I know how to do in Objective-C but am learning for first time Swift. However, my code is not getting the row from the index path or object.
Here is my code.
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
print("segue")
if segue.identifier == "showDetail"{
if let destinationVC = segue.destination as? detailVC {
)
if let indexPath = self.tableView.indexPathForSelectedRow {
print("row%#",indexPath)//Prints as nil
let thisItem = myItems[indexPath.row]//never gets here
destinationVC.item = thisItem
}
}
}
}
Can anyone see why I am not getting the row or the object? Thanks in advance for any suggestions.
Edit:
I got it to work with following:
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "showDetail" {
let indexPath: NSIndexPath = self.tableView.indexPathForSelectedRow! as NSIndexPath
let anItem: myItem = myItems[indexPath.row];
let destVC = segue.destination as? detailVC
destVC?.item = anItem
}
}
Implement UITableViewDelegate method,
func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
let item = myItems[indexPath.row]
self.performSegue(withIdentifier: "showDetail", sender: item)
}
then implement below,
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "showdetail" {
let detailController = segue.destination as! detailVC
detailController.item = sender as! Your_Item
}
}
Why don't you use these methods to save the value of the selected row or item? and then perform segue?
tableView(_:didDeselectRowAt:)
tableView(_:didSelectRowAt:)

How to send a selected collectionview cell to another view controller (ios)?

I'm being able to detect the selected row (image) in my collection view, But I need to send it to another view controller. Here is a part of the code :
func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
if let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "cell", for: indexPath) as? CollectionViewCell {
cell.cellImage.image = UIImage(named: images[indexPath.row])
return cell
} else {
return CollectionViewCell()
}
}
//Printinig the selected image ID in console
func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath)
{
SelectedItem = indexPath.row + 1
print(SelectedItem)
}
//Navigate to MPViewController
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
let DestViewController = segue.destination as! MPViewController
DestViewController.labelText = String(SelectedItem)
}
}
Initialize a variable first
var imageToPass: UIImage!
Then update didSelectItemAt func
func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath)
{
SelectedItem = indexPath.row + 1
print(SelectedItem)
self.imageToPass = UIImage(named: images[SelectedItem])
performSegue(withIdentifier: "TargetVC", sender: imageToPass) //here you give the identifier of target ViewController
}
Go to your TargetVC and initialize a variable
var getImage: UIImage!
Then override the function in previous VC
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "TargetVC" {
if let targetVC = segue.destination as? TargetVC {
if let imageToPass = sender as? UIImage {
TargetVC.getImage = imageToPass
}
}
}
}
//Printinig the selected image ID in console
func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath)
{
self.SelectedItem = indexPath.row + 1
self.selectedImage = UIImage(named: images[indexPath.row]);
print(SelectedItem)
}
//Navigate to MPViewController
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
let DestViewController = segue.destination as! MPViewController
DestViewController.imageSelected = self.selectedImage;
DestViewController.selectedItem = String(self.SelectedItem);
}
Now in MPViewController you can use the data self.imageSelected and self.selectedItem as per your requirements.
Take one instance variable in your destination class and set value of it in prepare for segue and then in viewDidload set that string to your label's text like,
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
let DestViewController = segue.destination as! MPViewController
DestViewController.yourText = String(SelectedItem)
}
ans in viewDidload
yourLabel.text = yourText

Usage of performSeguewithIdentifier Function in Dynamic Values Tableview

I can list datas in tableview. When I choose a row and trying to pass another view controller with showing specific data related to my pressed cell, It couldn't make it.
I didn't able to store data "selectedMeal" variable in prepareforsegue function, it always return [ ].
I think, my main problem is selecting the cell and sending to this cell to prepare for segue function. Perhaps, it has a problem in DispatchQueue.main.async function.
*When I try to pass to static data, it works great.
func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
if let cell = tableView.cellForRow(at: indexPath) {
cell.accessoryType = .checkmark;
DispatchQueue.main.async {
self.performSegue(withIdentifier: "gotoOrderDetail", sender: self)
}
}
}
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if (segue.identifier == "gotoOrderDetail") {
let DestViewController : OrderDetailListViewController = segue.destination as! OrderDetailListViewController
let selectedMeal = selectedCells.map { (index: Int) -> SavedMeal in
return savedMeal[index]
}
DestViewController.mealarray = selectedMeal
}
}
Try to use this code
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if (segue.identifier == "gotoOrderDetail") {
let DestViewController : OrderDetailListViewController = segue.destination as! OrderDetailListViewController
let path = self.tableView.indexPathForSelectedRow()! // get the selected indexPath
DestViewController.mealarray = savedMeal[path.row]
}
}
Try to use Sender parameter
you can you like this:
self.performSegue(withIdentifier: "gotoOrderDetail", sender: indexPath)
and then in prepare(for segue: sender?)
if (segue.identifier == "gotoOrderDetail") {
let DestViewController : OrderDetailListViewController = segue.destination as! OrderDetailListViewController
let index = sender as! Int
DestViewController.mealarray = savedMeal[index]
}
p/s: you do not need to use dispatch queue in this case

Preparing segue in Collection View

I have collection view implemented but have an error for the segue. I am trying to hand the image to another view controller using a segue. This is the code for it.
func collectionView(collectionView: UICollectionView, didSelectItemAtIndexPath indexPath: NSIndexPath)
{
self.performSegueWithIdentifier("showImage", sender: self)
}
override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?)
{
if segue.identifier == "showImage"
{
let indexPaths = self.collectionView!.indexPathsForSelectedItems()!
let indexPath = indexPaths[0] as NSIndexPath
let vc = segue.destinationViewController as! NewViewController
vc.image = self.imageArray[indexPath.row]!
vc.title = self.appleProducts[indexPath.row]
}
}
}
However I am having an error at collectionView!.indexPathsForSelectedItemssaying that Could not find member indexPathsForSelectedItems. Why is this happening and how should it be changed. Thank you
I have mode some changes to your code
Add following changes in your code
func collectionView(collectionView: UICollectionView, didSelectItemAtIndexPath indexPath: NSIndexPath)
{
self.performSegueWithIdentifier("showImage", sender: indexPath)
}
override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?)
{
if segue.identifier == "showImage"
{
let indexPath : NSIndexPath = sender as! NSIndexPath
let vc = segue.destinationViewController as! NewViewController
vc.image = self.imageArray[indexPath.row]!
vc.title = self.appleProducts[indexPath.row]
}
}

Resources