Using variable from one class in another class - swift

I have two classes: CollectionCell and ViewController.
The first class is used for Collection View Cell (in which I have placed a button). In CollectionCell class I need to connect outlet for this button: #IBOutlet weak var firstPercent: UIButton!.
In ViewController class I need to use var of this button: firstPercent.
How can I do that? Thanks for any help.

In collectionViewDelegate
- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath
Now declare your Custom Cell instance and then
you can use CollectionCell.firstPercent addTarget in ViewController and set this or
do whatever you want.

You can get it something like below.
func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "ZonesCell", for: indexPath as IndexPath) as! ZonesCell
let keyValue = self.dataList[indexPath.row] as! [String:Any]
cell.lblZoneName.text = keyValue[Keys.name] as? String
if(keyValue[Keys.status] as? Bool)! {
cell.lblZoneName.textColor = UIColor.white
} else {
cell.lblZoneName.textColor = UIColor.red
}
return cell
}
There lets suppose ZonesCell is the collectionCell contains lblZoneName as label.
You can use button same as label.

You can use delegate for this.
Add a protocol named “CollectionCellDelegate“ for your cell and add a delegate method for your button action. Pass cell itself as a parameter to that method. Conform to “CollectionCellDelegate“ from your ViewController and implement delegate method inside ViewController. Finally but most important step, assign your view controller as CollectionCellDelegate from cellForItemAt method.
protocol CollectionCellDelegate : class {
func didPressButtonFirstPercent(_ cell: CollectionCell)
}
//Inside your CollectionCell class declare a variable to hold your cell delegate
class CollectionCell: UICollectionViewCell {
//Add a variable to hold your delegate
weak var delegate: CollectionCellDelegate?
//Outlet for your button
#IBOutlet weak var firstPercent: UIButton!
//Action for your button
#IBAction func didPressButtonFirstPercent(_ sender: Any) {
delegate?.didPressButtonFirstPercent(self)
}
}
//ViewController Conform to CollectionCellDelegate
class ViewController: UIViewController, CollectionCellDelegate{
func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
let cell = collectionView.dequeueReusableCell(withReuseIdentifier: “Cell_Identifier”, for: indexPath) as! CollectionCell
//Set ViewController as your CollectionCell delegate
cell.delegate = self
return cell
}
//Implement delegate method here
func didPressButtonFirstPercent(_ cell: CollectionCell) {
//You can access your button here like below
Let firstPercent = cell.firstPercent
}
}

class ViewController: UIViewController, UICollectionViewDataSource, UICollectionViewDelegate{
func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
// get a reference to our storyboard cell
let cell = collectionView.dequeueReusableCell(withReuseIdentifier: reuseIdentifier, for: indexPath as IndexPath) as! CollectionCell
// Use the outlet in our custom class to get a reference to the UILabel in the cell
cell. firstPercent.tag = indexPath.row
example project
return cell
}
}

Related

Cell button tableView Swift

I have a tableView with Sections and every section got todoitems that u add.
I'm trying to animate in my picture on the todoItem I click with my cell button delegate function. But I really don't know how to connect to just that one item and make it animate.
What I'm trying to get access to is the same access to a cell like I do in didSelectRow but in this cellButtonFunction, since it's the button in the cell I'm gonna press on and not the whole cell.
The thing I wanna accomplish with pressing the button is like this example:
cellPressed.image.ishidden = false
cellPressed.image.animate()
This cell image have an animated class that works set to it, it's just that I need to hit the specific cell for this
Watched a few YouTube videos and researched but I don't get it to work, so I hope you guys can help me
extension ViewController: FirstTableViewCellDelegate {
func myImageButtonTapped(with index: IndexPath, view: AnimatedCheckmarkView) {
HapticsManager.shared.selectionVibrate()
let todo = self.tableViewCoreData[index.section].sortedItems[index.row - 1]
todo.isMarked = !todo.isMarked
if todo.isMarked == true {
self.tableViewCoreData[index.section].totalMarked += 1
view.animate(withDuration: 1.0, delay: 0.7)
view.isHidden = false
do {
try self.context.save()
}
catch{
//error
}
tableView.reloadData()
} else {
view.isHidden = true
self.tableViewCoreData[index.section].totalMarked -= 1
do {
try self.context.save()
}
catch{
//error
}
tableView.reloadData()
}
Here is the function. Litterly everything in this works except the view.animate() that animates one random view instead
First create delegate to receive action from cell
protocol CellDelegate:AnyObject{
/// pass arguments as per requirement
func cell(buttonDidPressed indexPath: IndexPath)
}
Now in your Cell class create weak reference of delegate
class Cell: UICollectionViewCell{
weak var delegate: CellDelegate? = nil
var indexPath: IndexPath!
/// code
#IBAction func buttonDidPressed(_ sender: UIButton) {
delegate?.cell(buttonDidPressed: indexPath)
}
}
now in ur controller confirm this protocol
extension ViewController: UICollectionViewDelegate,
UICollectionViewDataSource,
CellDelegate{
func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
// let cell : Cell dequeueReusableCell your cell
cell.delegate = self
cell.indexPath = indexPath
return cell
}
func cell(buttonDidPressed indexPath: IndexPath){
// your task on cell click
}
}
You can also use closures in cell class alternative to protocol

CollectionView pass data

What is the correct way to pass data from my ViewController to my CollectionViewItem?
ViewContoller
func collectionView(_ collectionView: NSCollectionView, itemForRepresentedObjectAt indexPath: IndexPath) -> NSCollectionViewItem {
let item = CollectionView.makeItem(withIdentifier: NSUserInterfaceItemIdentifier(rawValue: "CollectionViewItem"), for: indexPath) as! CollectionViewItem
item.themeName = getDirectoryContentByIndex(index: indexPath)
return item
}
CollectionViewItem
class CollectionViewItem: NSCollectionViewItem {
var themeName: String!
#IBOutlet weak var NameOfTheme: NSTextFieldCell!
override func viewDidLoad() {
super.viewDidLoad()
// Do view setup here.
}
}
Edit:
I want to assign the themeNameas stringValue of NameOfTheme. But if I set the value, the IBOutlet is nil.
I recommend you to make fields of your cell private and make configure(YOUR_PARAMS) (in our case configure(themeName: String). So in cellForRow you will call this function cell.configure(themeName: "")

Field an UITextField when button tapped in a UICollectionView

I gonna need your help to understand how to interact with an UITextField when button tapped.
This is my code in my ViewController:
override func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell
{
let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "cell", for: indexPath) as! MyCollectionViewCell
cell.addBookTapped.addTarget(self,action: #selector(buttonTapped(_:)),for: .touchUpInside)
cell.configureCell(with: books[indexPath.row], indexCell: indexPath.row )
return cell
}
func buttonTapped(_ sender: UIButton)
{
let tag = sender.tag
//Do Stuff
}
And in my MyCollectionViewCell, I configure all the button and textView and add tag in my button:
#IBOutlet weak var myTextFielThatIWantToFieldWhenButtonTapped: UITextField!
In my ViewController inside my func buttonTapped I can't reach myTextFielThatIWantToFieldWhenButtonTapped.
How can write something in it when the button is tapped and be visible directly on the view?
you have to get your intended cell by calling cellForItem at an indexPath of your specific cell like below: (for example your cell is in section 0 item 0 )
let indexPath = IndexPath(item: 0, section: 0)
let cell = collectionView.cellForItem(at: indexPath) as? YourCustomCollectionViewCellClass
then you can access your variables inside your cell class :
cell.myTextFielThatIWantToFieldWhenButtonTapped

Push TableViewController from a UICollectionView with UITableViewCell's

So I am trying to push a UITableViewController from a UITableViewCell that is embedded in a collection view cell.
So the structure is UICollectionView > UICollectionViewCell > UITableView > UITableViewCell.
Do I want to call a segue when the TableViewCell is clicked?
How can I do this as you cannot access the function perform segue for identifier?
You can create one protocol for that and implement it with your ViewController where you are having collectionView, after that make instance property of that protocol in your collectionViewCell and set that property in cellForItemAt method. Now inside the didSelectRowAt method of tableView call the delegate method with the detail that you want to pass for segue.
protocol PassData {
func performSegue(with data: String) //Set argument type to Type that you want pass instead of String
}
Now implement this PassData protocol with your ViewController and inside the cellForItemAt set the delegate of UICollectionViewCell.
class ViewController: UIViewController, PassData, UICollectionViewDelegate, UICollectionViewDataSource {
//Other methods
func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "cell", for: indexPath) as! CustomCollectionViewCell
cell.passDelegate = self
return cell
}
//Add the `performSegue(with:)` delegate method of PassData
func performSegue(with data: String) {
//Perform segue here
self.performSegue(withIdentifier: "SegueIdentifier", sender: data)
}
}
Now in your CustomCollectionViewCell make one instance property named passDelegate of type PassData? after that in didSelectRowAt method of tableView call its delegate method.
class CustomCollectionViewCell: UICollectionViewCell, UITableViewDelegate, UITableViewDataSource {
var passDelegate: PassData?
//Your other methods
func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
//Pass whatever data that you want to pass
self.passDelegate?.performSegue(with: array[indexPath.row])
}
}
You can push the tableViewController to navigation stack by calling self.navigationController?.pushViewController(tableviewVC, animate: true) from table view delegate method didSelectRowAtIndexPath

How to get the 'parent' of a focused cell in UIcollectionview cell with swift - tvOS

I made some sort of Netflix layout for my tvOS application, which contains several collection views named: featuredCollectionView and standardCollectionView.
I have a variable which contains the current focused cell. The only thing I want is to get the current collection view of selected cell. Can anyone help me with it?
The code
func pressedThePlayPauseButton() {
if let focusedCell = UIScreen.main.focusedView as? UICollectionViewCell{
let collectionViewOfFocusedCell = ...
You can always walk up the view hierarchy:
var parentCollectionView = self.superview
while parentCollectionView is UICollectionView != true {
parentCollectionView = parentCollectionView?.superview
}
You can change UICollectionView above to the subclass you are looking for if you need to go through multiple collection views. The easier way is to just give your cell a weak reference to your collectionView in cellForItemAtIndexPath; this also works for your view controller instead of your collectionView which is likely what you really want the reference to. It has to be weak since the collectionView retains the cell; otherwise you create a cycle.
class CustomCollectionViewCell: UICollectionViewCell {
weak var customCollectionViewController: CustomCollectionViewController?
}
class CustomCollectionViewController: UICollectionViewController {
override func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
let cell = collectionView.dequeueReusableCell(withReuseIdentifier: String(describing: CustomCollectionViewCell.self), for: indexPath) as! CustomCollectionViewCell
cell.customCollectionViewController = self
return cell
}
}