在 swift 2.2 中处理 Tableview 中的开关

Posted

技术标签:

【中文标题】在 swift 2.2 中处理 Tableview 中的开关【英文标题】:Dealing with switch in Tableview at swift 2.2 【发布时间】:2016-07-28 18:40:28 【问题描述】:

我有一个如下图所示的屏幕:

如您所见,我使用自定义单元格上传了带有学生姓名的列表,我希望在单击保存按钮时将学生的状态保存在数组中,我第一次为所有学生初始化了数组,当状态为开关已启用,然后单击的单元格索引处的此值转换为 1 但我无法做到这一点,当单击操作发生在开关上时,这仅在单击单元格(行)时发生,我如何才能做同样的事情只有更改开关状态以更新数组,而无需单击表中的完整行

主视图代码:

 import UIKit

 class teacherAttendanceVC: UIViewController , UITableViewDataSource,UITableViewDelegate  



@IBOutlet weak var studentlistTable: UITableView!

@IBOutlet weak var loadIndicator: UIActivityIndicatorView!


var username:String?
var classID: String?
var branchID: String?

var normal_id = [String]()
var student_name = [String]()

 var student_attendance = [String]()





//Sent Data
var n_id = ""
var stu_name = ""



@IBAction func backButton(sender: AnyObject) 

    self.dismissViewControllerAnimated(true, completion: nil )



override func viewDidLoad() 
    super.viewDidLoad()

    studentlistTable.delegate = self
    studentlistTable.dataSource = self


    let prefs:NSUserDefaults = NSUserDefaults.standardUserDefaults()
    username = prefs.objectForKey("user")as! String
    classID = prefs.objectForKey("ClassID")as! String
    branchID = prefs.objectForKey("BranchID")as! String




    self.loadIndicator.startAnimating()

    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0),  () -> Void in



        self.loadList()


        dispatch_async(dispatch_get_main_queue(),  () -> Void in
            self.loadIndicator.stopAnimating()
            self.studentlistTable.reloadData()


        )
    );





override func viewDidAppear(animated: Bool) 




func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int 

    return normal_id.count



func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell 
    //This method to define each cell at Table View

    let cell = self.studentlistTable.dequeueReusableCellWithIdentifier("cell", forIndexPath: indexPath) as! teacherAttendanceCell



    cell.studentNameLabel.text = student_name[indexPath.row]


    return cell



func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) 

    // Get Cell Label
    let currentCell = studentlistTable.cellForRowAtIndexPath(indexPath) as! teacherAttendanceCell!

    student_attendance[indexPath.row] = currentCell.status








@IBAction func saveButton(sender: AnyObject) 
    print(student_attendance) // this only to ensure from the final array before sending to server 



func loadList()

    var normallink = "myurl"
    normallink = normallink + "?classid=" + self.classID! + "&branchid=" + self.branchID!

    print(normallink)

    var studentParentURL:NSURL = NSURL (string: normallink)!
    let data = NSData(contentsOfURL: studentParentURL)!



    do 
        let json = try NSJSONSerialization.JSONObjectWithData(data, options: .AllowFragments)

        if let alldata = json["data"] as? [[String: AnyObject]] 
            for onedata in alldata 
                if let no_id = onedata["id"] as? String 
                    normal_id.append(no_id)
                
                if let s_name = onedata["studentName"] as? String 
                    student_name.append(s_name)
                




            
        
     catch 
        print("Error Serializing JSON: \(error)")
    

    if(normal_id.count != 0)
    
        for i in 1...self.normal_id.count
        
            self.student_attendance.append("0")
        
    




    print(normal_id.count)
    print(student_name.count)








单元格代码:

class teacherAttendanceCell: UITableViewCell 

@IBOutlet weak var studentNameLabel: UILabel!
@IBOutlet weak var attendSwitch: UISwitch!

var status:String = ""

override func awakeFromNib() 
    super.awakeFromNib()

    if(attendSwitch.on)
    
        status = "1"
        print("ON")
    
    else
        status = "0"
        print("OFF")

    

    attendSwitch.addTarget(self, action: "stateChanged:", forControlEvents: UIControlEvents.ValueChanged)




func stateChanged(switchState: UISwitch) 
    if switchState.on 
        status = "1"
        print("ON")
     else 
       status = "0"
        print("OFF")
    


override func setSelected(selected: Bool, animated: Bool) 
    super.setSelected(selected, animated: animated)


@IBAction func attendSwitchChanged(sender: AnyObject) 



更新:

主视图控制器:

import UIKit

class teacherAttendanceVC: UIViewController , UITableViewDataSource,UITableViewDelegate,CellInfoDelegate  



@IBOutlet weak var studentlistTable: UITableView!

@IBOutlet weak var loadIndicator: UIActivityIndicatorView!


var username:String?
var classID: String?
var branchID: String?

var normal_id = [String]()
var student_name = [String]()

 var student_attendance = [String]()





//Sent Data
var n_id = ""
var stu_name = ""



@IBAction func backButton(sender: AnyObject) 

    self.dismissViewControllerAnimated(true, completion: nil )



override func viewDidLoad() 
    super.viewDidLoad()

    studentlistTable.delegate = self
    studentlistTable.dataSource = self


    let prefs:NSUserDefaults = NSUserDefaults.standardUserDefaults()
    username = prefs.objectForKey("user")as! String
    classID = prefs.objectForKey("ClassID")as! String
    branchID = prefs.objectForKey("BranchID")as! String





    self.loadIndicator.startAnimating()

    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0),  () -> Void in



        self.loadList()



        dispatch_async(dispatch_get_main_queue(),  () -> Void in
            self.loadIndicator.stopAnimating()
            self.studentlistTable.reloadData()


        )
    );





override func viewDidAppear(animated: Bool) 




func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int 

    return normal_id.count



func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell 
    //This method to define each cell at Table View

    let cell = self.studentlistTable.dequeueReusableCellWithIdentifier("cell", forIndexPath: indexPath) as! teacherAttendanceCell
     cell.delegate = self




    cell.studentNameLabel.text = student_name[indexPath.row]
     student_attendance[indexPath.row] = cell.status


    //print(student_attendance.count)
    //let currentCell = studentlistTable.cellForRowAtIndexPath(indexPath) as! teacherAttendanceCell!
    // student_attendance.append(cell.status)

    return cell



func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) 

    // Get Cell Label
  //  let currentCell = studentlistTable.cellForRowAtIndexPath(indexPath) as! teacherAttendanceCell!

   // student_attendance[indexPath.row] = currentCell.status
    //print("OK Status here!" + String(student_attendance.count))







@IBAction func saveButton(sender: AnyObject) 
    print(student_attendance)



func loadList()

    var normallink = "mylinkhere"
    normallink = normallink + "?classid=" + self.classID! + "&branchid=" + self.branchID!

    print(normallink)

    var studentParentURL:NSURL = NSURL (string: normallink)!
    let data = NSData(contentsOfURL: studentParentURL)!


    do 
        let json = try NSJSONSerialization.JSONObjectWithData(data, options: .AllowFragments)

        if let alldata = json["data"] as? [[String: AnyObject]] 
            for onedata in alldata 
                if let no_id = onedata["id"] as? String 
                    normal_id.append(no_id)
                
                if let s_name = onedata["studentName"] as? String 
                    student_name.append(s_name)
                




            
        
     catch 
        print("Error Serializing JSON: \(error)")
    

    if(normal_id.count != 0)
    
        for i in 1...self.normal_id.count
        
            self.student_attendance.append("0")
        
    




    print(normal_id.count)
    print(student_name.count)




func processThatNumber(theStatus: String) 
    print("out : \(theStatus)")


protocol CellInfoDelegate 
func processThatNumber(theStatus: String)
 

单元格视图控制器:

import UIKit

class teacherAttendanceCell: UITableViewCell

@IBOutlet weak var studentNameLabel: UILabel!
@IBOutlet weak var attendSwitch: UISwitch!

var status:String = ""
var delegate: CellInfoDelegate?

override func awakeFromNib() 
    super.awakeFromNib()

    if(attendSwitch.on)
    
        status = "1"
        print("ON")
    
    else
        status = "0"
        print("OFF")

    

    attendSwitch.addTarget(self, action: "stateChanged:", forControlEvents: UIControlEvents.ValueChanged)




func stateChanged(switchState: UISwitch) 
    if switchState.on 
        status = "1"
        print("ON")
     else 
       status = "0"
        print("OFF")
    

    if let delegate = self.delegate 
        delegate.processThatNumber(self.status)
    


override func setSelected(selected: Bool, animated: Bool) 
    super.setSelected(selected, animated: animated)


@IBAction func attendSwitchChanged(sender: AnyObject) 



【问题讨论】:

【参考方案1】:

有几种方法可以做到这一点:使用closuredelegate,但我更喜欢使用delegate

    为您的teacherAttendanceCell 单元格创建一个delegate,就像在这个答案https://***.com/a/25792213/2739795 中一样

    让你teacherAttendanceVC符合delegate

    每次cellForRowAtIndexPath 调用设置cell.delegate = self。还将单元格返回到您的委托方法中

    内部委托调用方法stateChanged

    并且当委托方法调用时,如果切换单元格,您可以获得索引

tableView.indexPathForCell(cellFromParam)

【讨论】:

我更新了我的帖子,我对在 ios 中使用协议不是很熟悉,但是直到现在当我点击保存按钮时,我得到了相同的旧数组,所有项目都为零,但是当我切换开关时,我可以通过协议从主视图控制器打印状态值,但我不知道如何以及在何处获取单元格的索引来更改主视图控制器数组中此项的值 我解决了我之前说的问题,并依赖这篇文章采取实际步骤,因为正如我提到的,在那之前我没有处理协议***.com/questions/29913066/…

以上是关于在 swift 2.2 中处理 Tableview 中的开关的主要内容,如果未能解决你的问题,请参考以下文章

Swift 4 tableview 不使用通用完成处理程序显示数据

单击另一个按钮 swift 2.2 更改声音按钮图像

通过 try 块处理 Swift 2.2 错误

如何在 Swift 中从 Detail ViewController 更新 tableview 数组

为啥要处理单击 TableView Swift IOS 值得单元格行之前单击的行? [复制]

无法让 API 调用及时运行 tableview swift 4 xcode 9