{"id":2399,"date":"2017-04-04T15:10:24","date_gmt":"2017-04-04T09:40:24","guid":{"rendered":"https:\/\/www.innovationm.com\/blog\/?p=2399"},"modified":"2017-04-04T15:10:24","modified_gmt":"2017-04-04T09:40:24","slug":"handling-dynamic-views-in-table-view-cell","status":"publish","type":"post","link":"https:\/\/www.innovationm.com\/blog\/handling-dynamic-views-in-table-view-cell\/","title":{"rendered":"Handling Dynamic Views in Table View Cell"},"content":{"rendered":"<p>&nbsp;<\/p>\n<p><span style=\"font-weight: 400;\">In educational applications we often come to a situation when we have to create a user interface for multiple answer type questions. If each question have same number of answers then it can be created very easily by creating a reusable cell in storyboard but what if number of answers in each question varies? <\/span><\/p>\n<p><span style=\"font-weight: 400;\">In this post we will see how we can make use of TableView in iOS to create an user interface in which each cell of TableView can have multiple options. This project will be created in XCode 8.1 and Swift 3.0.<\/span><\/p>\n<p><span style=\"font-weight: 400;\">We will use following three components to accomplish this:<\/span><\/p>\n<ul>\n<li style=\"font-weight: 400; text-align: left;\"><span style=\"font-weight: 400;\">UITableView<\/span><\/li>\n<li style=\"font-weight: 400;\"><span style=\"font-weight: 400;\">CheckableTableViewCell: Subclass of UITableViewCell<\/span><\/li>\n<li style=\"font-weight: 400;\"><span style=\"font-weight: 400;\">CheckableOptionView: Subclass of UIView<\/span><\/li>\n<\/ul>\n<h2><span style=\"font-weight: 400;\">CheckableOptionView:<\/span><\/h2>\n<p><span style=\"font-weight: 400;\">Lets create a subclass of UIView by <\/span><b>File&gt;New&gt;File&gt;Cocoa Touch Class. <\/b><span style=\"font-weight: 400;\">Give the name <\/span><b>CheckableOptionView<\/b><span style=\"font-weight: 400;\"> and make it subclass of <\/span><b>UIView. <\/b><span style=\"font-weight: 400;\">Click Next and Create to create the .swift file. It will create a file with following code:<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">class CheckableOptionView: UIView {\r\n\/*\r\n\u00a0 \u00a0 \/\/ Only override draw() if you perform custom drawing.\r\n\u00a0 \u00a0 \/\/ An empty implementation adversely affects performance during animation.\r\n\u00a0 \u00a0 override func draw(_ rect: CGRect) {\r\n\u00a0 \u00a0\u00a0 \u00a0 \/\/ Drawing code\r\n\u00a0 \u00a0 }\r\n*\/\r\n}<\/pre>\n<p><span style=\"font-weight: 400;\">Delete the commented code, we are not gonna use it.<\/span><\/p>\n<p><span style=\"font-weight: 400;\">Now create following initializers in CheckableOptionView:<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">init(index: Int) {\r\n\u00a0 \u00a0 super.init(frame: .zero)\r\n\u00a0 \u00a0 initializeView(index: index)\r\n}\r\n\r\nrequired init?(coder aDecoder: NSCoder) {\r\n\u00a0 \u00a0 fatalError(\"init(coder:) has not been implemented\")\r\n}<\/pre>\n<p>Now we will implement the initializeView(index:) method. But before implementing this method create a label and a button object in this class and a constant value to use for button tag.<\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">private var checkableButton: UIButton!\r\nprivate var labelOption: UILabel!\r\nprivate let buttonTag: Int = 8080<\/pre>\n<p><span style=\"font-weight: 400;\">Let&#8217;s create initializeView method.<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">private func initializeView(index: Int) {\r\n}<\/pre>\n<p><span style=\"font-weight: 400;\">Create UIButton object and set tag with given index.<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">checkableButton = UIButton(type: .custom)\r\ncheckableButton.tag = buttonTag + index<\/pre>\n<p><span style=\"font-weight: 400;\">Now set the button image for different states<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">checkableButton.setImage(UIImage(named: \u201cunchecked\u201d), for: .normal)\r\ncheckableButton.setImage(UIImage(named: \u201cchecked\u201d), for: .selected)<\/pre>\n<p><span style=\"font-weight: 400;\">Add action target to button<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">checkableButton.addTarget(self, action: #selector(optionSelected(sender:)), for: .touchUpInside)<\/pre>\n<p><span style=\"font-weight: 400;\">Now create the option label which can have multiple lines<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">labelOption = UILabel()\r\nlabelOption.numberOfLines = 0\r\nlabelOption.lineBreakMode = .byWordWrapping<\/pre>\n<p>Add Label and Button to the view:<\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">addSubview(checkableButton)\r\naddSubview(labelOption)<\/pre>\n<p><span style=\"font-weight: 400;\">Now disable converting auto resizing masks to constraint for each view:<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">translatesAutoresizingMaskIntoConstraints = false\r\ncheckableButton.translatesAutoresizingMaskIntoConstraints = false\r\nlabelOption.translatesAutoresizingMaskIntoConstraints = false<\/pre>\n<p><span style=\"font-weight: 400;\">Add following constraints to Button:<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">\/\/Height = 30\r\ncheckableButton.heightAnchor.constraint(equalToConstant: 30).isActive = true\r\n\r\n\/\/Width = 30\r\ncheckableButton.widthAnchor.constraint(equalToConstant: 30).isActive = true\r\n\r\n\/\/Leading = 8\r\ncheckableButton.leadingAnchor.constraint(equalTo: leadingAnchor, constant: 8).isActive = true\r\n\r\n\/\/Vertically center\r\ncenterYAnchor.constraint(equalTo: checkableButton.centerYAnchor).isActive = true<\/pre>\n<p>Add following constraints to Label:<\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">\/\/Lable leading = button trailing + 8\r\nlabelOption.leadingAnchor.constraint(equalTo: checkableButton.trailingAnchor, constant: 8).isActive = true\r\n\r\n\/\/Top = 8\r\nlabelOption.topAnchor.constraint(equalTo: topAnchor, constant: 8).isActive = true\r\n\r\n\/\/Trailing = 8\r\ntrailingAnchor.constraint(equalTo: labelOption.trailingAnchor, constant: 8).isActive = true\r\n\r\n\/\/Bottom = 8\r\nbottomAnchor.constraint(equalTo: labelOption.bottomAnchor, constant: 8).isActive = true<\/pre>\n<p><span style=\"font-weight: 400;\">Now create a protocol for a delegate call to cell as follows and also create a weak property to store the delegate.<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">protocol CheckableOptionViewDelegate: class {\r\n\u00a0 \u00a0 func checkableOptionView(option: Int)\r\n}\r\n\r\npublic weak var delegate: CheckableOptionViewDelegate?<\/pre>\n<p><span style=\"font-weight: 400;\">Now create following properties for multiple operations:<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">\/\/To mark an option selected\r\npublic var selected: Bool = false {\r\n\u00a0 \u00a0 didSet {\r\n\u00a0 \u00a0\u00a0 \u00a0 setSelected(selected: selected)\r\n\u00a0 \u00a0 }\r\n}\r\n\r\n\/\/To set the option text\r\npublic var optionText: String = \"\" {\r\n\u00a0 \u00a0 didSet {\r\n\u00a0 \u00a0\u00a0 \u00a0 setOptionText(text: optionText)\r\n\u00a0 \u00a0 }\r\n}\r\n\r\n\/\/To get the index of the option\r\npublic var option: Int {\r\n\u00a0 \u00a0 get {\r\n\u00a0 \u00a0     return checkableButton.tag - buttonTag\r\n\u00a0 \u00a0 }\r\n}\r\n\r\n\/\/To set whether option can be selected or not\r\npublic var optionSelectable: Bool = true {\r\n\u00a0 \u00a0 didSet {\r\n\u00a0\u00a0 \u00a0 \u00a0 if !optionSelectable {\r\n\u00a0 \u00a0\u00a0\u00a0 \u00a0 \u00a0 checkableButton.isSelected = false\r\n\u00a0 \u00a0\u00a0 \u00a0 }\r\n\u00a0 \u00a0 }\r\n}<\/pre>\n<p><span style=\"font-weight: 400;\">Now create the method setSelected and setOptionText<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">public func setOptionText(text: String) {\r\n\u00a0 \u00a0 labelOption.text = text\r\n}\r\n\r\npublic func setSelected(selected: Bool) {\r\n\u00a0 \u00a0 if !optionSelectable {\r\n\u00a0 \u00a0\u00a0 \u00a0 return\r\n\u00a0 \u00a0 }\r\n\r\n\u00a0 \u00a0 if selected {\r\n\u00a0 \u00a0\u00a0 \u00a0 checkableButton.isSelected = true\r\n\u00a0 \u00a0 } else {\r\n\u00a0 \u00a0\u00a0 \u00a0 checkableButton.isSelected = false\r\n\u00a0 \u00a0 }\r\n}<\/pre>\n<p><span style=\"font-weight: 400;\">Let&#8217;s create the action method of option button<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">@objc private func optionSelected(sender: UIButton) {\r\n\r\n\u00a0 \u00a0 if !optionSelectable {\r\n\u00a0 \u00a0\u00a0 \u00a0 return\r\n\u00a0 \u00a0 }\r\n\r\n\u00a0 \u00a0 if !sender.isSelected {\r\n\u00a0 \u00a0\u00a0 \u00a0 sender.isSelected = true\r\n\r\n\u00a0 \u00a0\u00a0 \u00a0 \/\/Call delegate method\r\n\u00a0 \u00a0\u00a0 \u00a0 delegate?.checkableOptionView(option: sender.tag - buttonTag)\r\n\u00a0 \u00a0 }\r\n}<\/pre>\n<p><span style=\"font-weight: 400;\">That\u2019s it. Our CheckableOptionView class is complete.<\/span><\/p>\n<h2><span style=\"font-weight: 400;\">CheckableTableViewCell:<\/span><\/h2>\n<p><span style=\"font-weight: 400;\">Lets create a subclass of <\/span><b>UITableViewCell<\/b><span style=\"font-weight: 400;\"> by <\/span><b>File&gt;New&gt;File&gt;Cocoa Touch Class. <\/b><span style=\"font-weight: 400;\">Give the name <\/span><b>CheckableTableViewCell<\/b><span style=\"font-weight: 400;\"> and make it subclass of <\/span><b>UITableViewCell. <\/b><span style=\"font-weight: 400;\">Click Next and Create to create the .swift file.<\/span><\/p>\n<p><span style=\"font-weight: 400;\">Change the initial code so that it should have following code:<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true \">class CheckableTableViewCell: UITableViewCell {\r\n\r\n\u00a0 \u00a0 override func awakeFromNib() {\r\n\u00a0 \u00a0\u00a0 \u00a0 super.awakeFromNib()\r\n\u00a0 \u00a0\u00a0 \u00a0 initializeCell()\r\n\u00a0 \u00a0 }\r\n\r\n}<\/pre>\n<p><span style=\"font-weight: 400;\">Now, let&#8217;s create following private variables to create a header and footer for question and answer for a cell:<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">private let headerView = UIView()\r\nprivate let footerView = UIView()\r\nprivate let headerLabel = UILabel()\r\nprivate let footerLabel = UILabel()<\/pre>\n<p><span style=\"font-weight: 400;\">Here, header label and view will be used for displaying question and footer label and view will be used to display answer.<\/span><\/p>\n<p><span style=\"font-weight: 400;\">Now, it\u2019s time to define the initializeCell method. In this method we will initialize header and footer view and add constraints to them. Initially the footer view will be invisible to user to hide the answer.<\/span><\/p>\n<p><span style=\"font-weight: 400;\">Create following method:<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">private func initializeCell() {\r\n}<\/pre>\n<p><span style=\"font-weight: 400;\">Make header label and footer label number of lines to zero and line break mode to word wrapping so that we can display multiple lines in it. Finally add them to cell\u2019s contentView as subview.<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">headerLabel.numberOfLines = 0\r\nheaderLabel.lineBreakMode = .byWordWrapping\r\n\r\nfooterLabel.numberOfLines = 0\r\nfooterLabel.lineBreakMode = .byWordWrapping\r\n\r\nheaderView.addSubview(headerLabel)\r\nfooterView.addSubview(footerLabel)\r\n\r\ncontentView.addSubview(headerView)\r\ncontentView.addSubview(footerView)<\/pre>\n<p><span style=\"font-weight: 400;\">Set background of footer view (Answer) to green. (Or any color you like).<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">footerView.backgroundColor = UIColor.green<\/pre>\n<p><span style=\"font-weight: 400;\">Now disable the auto resizing masks to convert into constraint for each view by following code:<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">headerView.translatesAutoresizingMaskIntoConstraints = false\r\nfooterView.translatesAutoresizingMaskIntoConstraints = false\r\nheaderLabel.translatesAutoresizingMaskIntoConstraints = false\r\nfooterLabel.translatesAutoresizingMaskIntoConstraints = false<\/pre>\n<p><span style=\"font-weight: 400;\">Let&#8217;s add constraint to Question View(Header).<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">\/\/headerLabel.top = headerView.top + 8\r\nheaderLabel.topAnchor.constraint(equalTo: headerView.topAnchor, constant: 8).isActive = true\r\n\r\n\/\/headerLabel.leading = headerView.leading + 8\r\nheaderLabel.leadingAnchor.constraint(equalTo: headerView.leadingAnchor, constant: 8).isActive = true\r\n\r\n\/\/headerView.trailing = headerLabel.trailing + 8\r\nheaderView.trailingAnchor.constraint(equalTo: headerLabel.trailingAnchor, constant: 8).isActive = true\r\n\r\n\/\/headerView.bottom = headerLabel.bottom + 8\r\nheaderView.bottomAnchor.constraint(equalTo: headerLabel.bottomAnchor, constant: 8).isActive = true\r\n\r\n\/\/headerView.leading = contentView.leading + 8\r\nheaderView.leadingAnchor.constraint(equalTo: contentView.leadingAnchor, constant: 8).isActive = true\r\n\r\n\/\/headerView.top = contentView.top + 8\r\nheaderView.topAnchor.constraint(equalTo: contentView.topAnchor, constant: 8).isActive = true\r\n\r\n\/\/contentView.trailing = headerView.trailing + 8\r\ncontentView.trailingAnchor.constraint(equalTo: headerView.trailingAnchor, constant: 8).isActive = true<\/pre>\n<p>Add following constraints to Answer View(Footer).<\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">\/\/footerLabel.leading = footerView.leading + 8\r\nfooterLabel.leadingAnchor.constraint(equalTo: footerView.leadingAnchor, constant: 8).isActive = true\r\n\r\n\/\/footerLabel.top = footerView.top + 8\r\nfooterLabel.topAnchor.constraint(equalTo: footerView.topAnchor, constant: 8).isActive = true\r\n\r\n\/\/footerVoew.trailing = footerLabel.trailing + 8\r\nfooterView.trailingAnchor.constraint(equalTo: footerLabel.trailingAnchor, constant: 8).isActive = true\r\n\r\n\/\/footerView.bottom = footerLabel.bootom + 8\r\nfooterView.bottomAnchor.constraint(equalTo: footerLabel.bottomAnchor, constant: 8).isActive = true\r\n\r\n\/\/footerView.leading = contentView.leading + 8\r\nfooterView.leadingAnchor.constraint(equalTo: contentView.leadingAnchor, constant: 8).isActive = true\r\n\r\n\/\/contentView.bottom = footerView.bottom + 8\r\ncontentView.bottomAnchor.constraint(equalTo: footerView.bottomAnchor, constant: 8).isActive = true\r\n\r\n\/\/contentView.trailing = footerView.trailing + 8\r\ncontentView.trailingAnchor.constraint(equalTo: footerView.trailingAnchor, constant: 8).isActive = true<\/pre>\n<p><span style=\"font-weight: 400;\">Cell initialization is done here. Let&#8217;s create some properties which can be used for different operations on the cell.(Methods used in these properties will be defined later in the post).<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">\/\/Set the options in a question.\r\npublic var options: Array&lt;String&gt; = [] {\r\n\u00a0 \u00a0 didSet {\r\n\u00a0 \u00a0\u00a0 \u00a0 addOptions(options: options)\r\n\u00a0 \u00a0 }\r\n}\r\n\r\n\/\/Set the selected option index.\r\npublic var selectedOption: Int = -1 {\r\n\u00a0 \u00a0 didSet {\r\n\u00a0 \u00a0\u00a0 \u00a0 setSelectedOption(index: selectedOption)\r\n\u00a0 \u00a0 }\r\n}\r\n\r\n\/\/Set the question string of the cell.\r\npublic var question: String = \"\" {\r\n\u00a0 \u00a0 didSet {\r\n\u00a0 \u00a0\u00a0 \u00a0 headerLabel.text = question\r\n\u00a0 \u00a0 }\r\n}\r\n\r\n\/\/Set the answer string for that question.\r\npublic var answer: String = \"\" {\r\n\u00a0 \u00a0 didSet {\r\n\u00a0 \u00a0\u00a0 \u00a0 footerLabel.text = answer\r\n\u00a0 \u00a0 }\r\n}\r\n\r\n\/\/Set whether the options are selectable or not.\r\npublic var optionSelectable: Bool = true {\r\n\u00a0 \u00a0 didSet {\r\n\u00a0 \u00a0\u00a0 \u00a0 setOption(selectable: optionSelectable)\r\n\u00a0 \u00a0 }\r\n}<\/pre>\n<p><span style=\"font-weight: 400;\">Now, let&#8217;s create the method setSelectedOption(index: selectedOption).<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">public func setSelectedOption(index: Int) {\r\n\u00a0 \u00a0 \/\/If options are not selectable do nothing.\r\n\u00a0 \u00a0 if !optionSelectable {\r\n\u00a0 \u00a0\u00a0 \u00a0 return\r\n\u00a0 \u00a0 }\r\n\r\n\u00a0 \u00a0 \/\/ Find all subviews\r\n\u00a0 \u00a0 for subview in contentView.subviews {\r\n\u00a0 \u00a0\u00a0 \u00a0 \/\/If it is CheckableOptionView\r\n\u00a0 \u00a0\u00a0 \u00a0 if let checkableOptionView = subview as? CheckableOptionView {\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 \/\/If the option index is equal to given index mark it as selected otherwise mark it as deselected.\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 if checkableOptionView.option == index {\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 checkableOptionView.selected = true\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 } else {\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 checkableOptionView.selected = false\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 }\r\n\u00a0 \u00a0\u00a0 \u00a0 }\r\n\u00a0 \u00a0 }\r\n}<\/pre>\n<p><span style=\"font-weight: 400;\">Let&#8217;s create a method to clear the selection for entire row. In this method we will find all the subviews of the content view of cell(Line 2). If the subview is type of CheckableOptionView(Line 3) then we will deselect that option.<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">public func clearSelection() {\r\n\u00a0 \u00a0 for subview in contentView.subviews {\r\n\u00a0 \u00a0\u00a0 \u00a0 if let checkableOptionView = subview as? CheckableOptionView {\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 checkableOptionView.selected = false\r\n\u00a0 \u00a0\u00a0 \u00a0 }\r\n\u00a0 \u00a0 }\r\n}<\/pre>\n<p><span style=\"font-weight: 400;\">This method will be used to mark the CheckableOptionView that whether it is selectable or not.<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">public func setOption(selectable: Bool) {\r\n\u00a0 \u00a0 \/\/Find each subview and check if it is of type CheckableOptionView, set the selectability of that view.\r\n\u00a0 \u00a0 for subview in contentView.subviews {\r\n\u00a0 \u00a0\u00a0 \u00a0 if let checkableOptionView = subview as? CheckableOptionView {\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 checkableOptionView.optionSelectable = selectable\r\n\u00a0 \u00a0\u00a0 \u00a0 }\r\n\u00a0 \u00a0 }\r\n}<\/pre>\n<p><span style=\"font-weight: 400;\">Let&#8217;s create a method to change the background color of any option. It will have two parameters color and the index of the option which background color has to be change. In this method we will find all the subviews of cell\u2019s content view and check if it is of type CheckableOptionView(Line 2 and 3) then we check that the option index of that view is equal to the given index(Line 4). If it is true then we will set the background color of that view to the given color in method parameter.<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">public func setBackground(color: UIColor, forOption option: Int) {\r\n\u00a0 \u00a0 for subview in contentView.subviews {\r\n\u00a0 \u00a0\u00a0 \u00a0 if let checkableOptionView = subview as? CheckableOptionView {\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 if checkableOptionView.option == option {\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 checkableOptionView.backgroundColor = color\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 }\r\n\u00a0 \u00a0\u00a0 \u00a0 }\r\n\u00a0 \u00a0 }\r\n}<\/pre>\n<p><span style=\"font-weight: 400;\">Following method can be used to set the Question Text.<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">public func setQuestion(question: String) {\r\n\u00a0 \u00a0 headerLabel.text = question\r\n}<\/pre>\n<p><span style=\"font-weight: 400;\">Following method can be used to set the Answer Text.<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">public func setAnswer(answer: String) {\r\n\u00a0 \u00a0 footerLabel.text = answer\r\n}<\/pre>\n<p><span style=\"font-weight: 400;\">Let&#8217;s create a method to show the answer of the question. In this method we will find all the constraints in the footerView(Line 2) and check if it is a height constraint(Line 3). If the constraint is of height then we will disable that constraint(Line 4).<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">public func showAnswer() {\r\n\u00a0 \u00a0 for constraint in footerView.constraints {\r\n\u00a0 \u00a0\u00a0 \u00a0 if constraint.firstAnchor == footerView.heightAnchor {\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 constraint.isActive = false\r\n\u00a0 \u00a0\u00a0 \u00a0 }\r\n\u00a0 \u00a0 }\r\n}<\/pre>\n<p><span style=\"font-weight: 400;\">Now, let&#8217;s create the method <\/span><b>addOptions(options: [String]) <\/b><span style=\"font-weight: 400;\">to add the options of question for the cell, it will take an array of strings:<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">public func addOptions(options: [String]) {\r\n\r\n\u00a0 \u00a0 \/\/ Store previous option view to add constraints\r\n\u00a0 \u00a0 var previousView: CheckableOptionView? = nil\r\n\r\n\u00a0 \u00a0 var i=0\r\n\u00a0 \u00a0 var isFirst = true\r\n\r\n\u00a0 \u00a0 \/\/ For all options given in the array\r\n\u00a0 \u00a0 while i &lt; options.count {\r\n\r\n\u00a0 \u00a0\u00a0 \u00a0 \/\/ If view is already exist (Due to reusability of \u00a0cell)\r\n\u00a0 \u00a0\u00a0 \u00a0 if let optionView = contentView.subviews[safe: i+2] as? CheckableOptionView {\r\n\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 \/\/Reset the view with given parameters\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 optionView.optionText = options[i]\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 optionView.optionSelectable = optionSelectable\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 optionView.selected = false\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 optionView.backgroundColor = UIColor.white\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 previousView = optionView\r\n\u00a0 \u00a0\u00a0 \u00a0 } else { \/\/ If view is not available create a new view and add constraints.\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 let optionView = CheckableOptionView(index: i)\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 optionView.optionText = options[i]\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 optionView.delegate = self\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 optionView.optionSelectable = optionSelectable\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 contentView.addSubview(optionView)\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 optionView.leadingAnchor.constraint(equalTo: contentView.leadingAnchor, constant: 8).isActive = true\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 if let previous = previousView {\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 if isFirst { \/\/ Remove the bottom constraint of previous view with footer view\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 for constraint in contentView.constraints {\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 if constraint.firstAnchor == footerView.topAnchor {\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 constraint.isActive = false\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 }\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 }\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 }\r\n\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 \/\/ Add top constraint to bottom of previous view\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 optionView.topAnchor.constraint(equalTo: previous.bottomAnchor).isActive = true\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 } else {\r\n\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 \/\/If previous view is not available then add top constraint to header view\u2019s bottom.\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 optionView.topAnchor.constraint(equalTo: headerView.bottomAnchor, constant: 8).isActive = true\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 }\r\n\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 \/\/ Add leading and trailing constraint to content view.\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 contentView.trailingAnchor.constraint(equalTo: optionView.trailingAnchor, constant: 8).isActive = true\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 optionView.heightAnchor.constraint(greaterThanOrEqualToConstant: 30).isActive = true\r\n\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 isFirst = false\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 previousView = optionView\r\n\u00a0 \u00a0\u00a0 \u00a0 }\r\n\u00a0 \u00a0\u00a0 \u00a0 i = i + 1\r\n\u00a0 \u00a0 }\r\n\r\n\u00a0 \u00a0 if let previous = previousView {\r\n\r\n\u00a0 \u00a0\u00a0 \u00a0 \/\/ Add last view\u2019s bottom to top of the footer view.\r\n\u00a0 \u00a0\u00a0 \u00a0 footerView.topAnchor.constraint(equalTo: previous.bottomAnchor, constant: 8).isActive = true\r\n\u00a0 \u00a0 }\r\n\r\n\u00a0 \u00a0 \/\/ Initially hide the footer view (Answer View)\r\n\u00a0 \u00a0 footerView.heightAnchor.constraint(equalToConstant: 0).isActive = true\r\n\r\n\u00a0 \u00a0 \/\/ If there are more view\u2019s than the given options remove them. (Due to reusability of cell).\r\n\u00a0 \u00a0 while i &lt; contentView.subviews.count - 2 {\r\n\u00a0 \u00a0\u00a0 \u00a0 if let optionView = contentView.subviews[safe: i+2] as? CheckableOptionView {\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 optionView.removeFromSuperview()\r\n\u00a0 \u00a0\u00a0 \u00a0 }\r\n\u00a0 \u00a0 }\r\n}<\/pre>\n<p><span style=\"font-weight: 400;\">Now, let&#8217;s create a protocol for delegate call to view controller:<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">protocol CheckableTableViewCellDelegate: class {\r\n\u00a0 \u00a0 func checkableTableViewCell(_ cell: CheckableTableViewCell, option: Int)\r\n}<\/pre>\n<p><span style=\"font-weight: 400;\">Let&#8217;s implement the <\/span><b>CheckableOptionViewDelegate <\/b><span style=\"font-weight: 400;\">as follows:<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">extension CheckableTableViewCell: CheckableOptionViewDelegate {\r\n\u00a0 \u00a0 func checkableOptionView(option: Int) {\r\n\r\n\u00a0 \u00a0\u00a0 \u00a0 \/\/Deselect all other options\r\n\u00a0 \u00a0\u00a0 \u00a0 for subview in contentView.subviews {\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 if let checkableOptionView = subview as? CheckableOptionView {\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 if checkableOptionView.option != option {\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 checkableOptionView.selected = false\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 }\r\n\u00a0 \u00a0\u00a0 \u00a0\u00a0 \u00a0 }\r\n\u00a0 \u00a0\u00a0 \u00a0 }\r\n\r\n\u00a0 \u00a0\u00a0 \u00a0 \/\/ Call delegate method to inform view controller.\r\n\u00a0 \u00a0\u00a0 \u00a0 delegate?.checkableTableViewCell(self, option: option)\r\n\u00a0 \u00a0 }\r\n}<\/pre>\n<p><span style=\"font-weight: 400;\">Add following extension to safely access the array elements:<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">extension Collection where Indices.Iterator.Element == Index {\r\n\r\n\u00a0 \u00a0 \/\/ Return object if present otherwise nil.\r\n\u00a0 \u00a0 subscript (safe index: Index) -&gt; Generator.Element? {\r\n\u00a0 \u00a0\u00a0 \u00a0 return indices.contains(index) ? self[index] : nil\r\n\u00a0 \u00a0 }\r\n}<\/pre>\n<h2><span style=\"font-weight: 400;\">Table View Implementation:<\/span><\/h2>\n<p><span style=\"font-weight: 400;\">To use the given CheckableTableViewCell, add a UITableView from storyboard and set the class of the reusable cell to CheckableTableViewCell as given screenshot:<\/span><\/p>\n<p><a href=\"https:\/\/www.innovationm.com\/blog\/wp-content\/uploads\/2017\/01\/Screen4.png\"><img fetchpriority=\"high\" decoding=\"async\" class=\"wp-image-2410 aligncenter\" src=\"https:\/\/www.innovationm.com\/blog\/wp-content\/uploads\/2017\/01\/Screen4.png\" alt=\"Screen4\" width=\"698\" height=\"447\" srcset=\"https:\/\/www.innovationm.com\/blog\/wp-content\/uploads\/2017\/01\/Screen4.png 1003w, https:\/\/www.innovationm.com\/blog\/wp-content\/uploads\/2017\/01\/Screen4-300x192.png 300w, https:\/\/www.innovationm.com\/blog\/wp-content\/uploads\/2017\/01\/Screen4-624x399.png 624w\" sizes=\"(max-width: 698px) 100vw, 698px\" \/><\/a><\/p>\n<p><span style=\"font-weight: 400;\">Now, add the following code in the viewDidLoad of your view controller:<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">tableView.estimatedRowHeight = 44 \/\/Or any value you want.\r\ntableView.rowHeight = UITableViewAutomaticDimension\r\ntableView.dataSource = self\r\ntableView.delegate = self<\/pre>\n<p><span style=\"font-weight: 400;\">In <\/span><b>cellForRowAt indexPath<\/b><span style=\"font-weight: 400;\"> method use following code:<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">\/\/Dequeue the cell. Replace `cell` with your reusable identifier\r\nlet cell = tableView.dequeueReusableCell(withIdentifier: \"cell\") as! CheckableTableViewCell\r\n\r\ncell.delegate = self\r\n\r\ncell.question = \u201cQuestion Text\u201d\r\ncell.options = [\u201cOption1\u201d, \u201cOption2\u201d, \u201cOption3\u201d] \/\/ Option array\r\ncell.answer = \"Answer Text\"<\/pre>\n<p><span style=\"font-weight: 400;\">If you want to mark an option selected use following code:<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true \">cell.selectedOption = 1 \/\/ Starts with index 0.<\/pre>\n<p>To show the answer of the question use following code:<\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true\">cell.showAnswer()<\/pre>\n<p><span style=\"font-weight: 400;\">To change the background color of any option use following code:<\/span><\/p>\n<pre class=\"theme:sublime-text lang:swift decode:true \">cell.setBackground(color: UIColor.red, forOption: 1)<\/pre>\n<p>That&#8217;s it. You are ready to go. Compile and run the project.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>&nbsp; In educational applications we often come to a situation when we have to create a user interface for multiple answer type questions. If each question have same number of answers then it can be created very easily by creating a reusable cell in storyboard but what if number of answers in each question varies? [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":2995,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[3,71],"tags":[160,122,89,165,178,10],"class_list":["post-2399","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-ios","category-mobile","tag-ios","tag-ipad","tag-iphone","tag-mobile","tag-swift-3-0","tag-ui-design"],"yoast_head":"<!-- This site is optimized with the Yoast SEO plugin v27.4 - https:\/\/yoast.com\/product\/yoast-seo-wordpress\/ -->\n<title>Handling Dynamic Views in Table View Cell | InnovationM Blog<\/title>\n<meta name=\"description\" content=\"In this post we will see how we can make use of Table View in iOS to create an user interface in which each cell of TableView can have multiple options.\" \/>\n<meta name=\"robots\" content=\"index, follow, max-snippet:-1, max-image-preview:large, max-video-preview:-1\" \/>\n<link rel=\"canonical\" href=\"https:\/\/www.innovationm.com\/blog\/handling-dynamic-views-in-table-view-cell\/\" \/>\n<meta property=\"og:locale\" content=\"en_US\" \/>\n<meta property=\"og:type\" content=\"article\" \/>\n<meta property=\"og:title\" content=\"Handling Dynamic Views in Table View Cell | InnovationM Blog\" \/>\n<meta property=\"og:description\" content=\"In this post we will see how we can make use of Table View in iOS to create an user interface in which each cell of TableView can have multiple options.\" \/>\n<meta property=\"og:url\" content=\"https:\/\/www.innovationm.com\/blog\/handling-dynamic-views-in-table-view-cell\/\" \/>\n<meta property=\"og:site_name\" content=\"InnovationM - Blog\" \/>\n<meta property=\"article:published_time\" content=\"2017-04-04T09:40:24+00:00\" \/>\n<meta property=\"og:image\" content=\"https:\/\/www.innovationm.com\/blog\/wp-content\/uploads\/2017\/02\/Dynamic-Table-View-Cell.png\" \/>\n\t<meta property=\"og:image:width\" content=\"624\" \/>\n\t<meta property=\"og:image:height\" content=\"347\" \/>\n\t<meta property=\"og:image:type\" content=\"image\/png\" \/>\n<meta name=\"author\" content=\"InnovationM Admin\" \/>\n<meta name=\"twitter:label1\" content=\"Written by\" \/>\n\t<meta name=\"twitter:data1\" content=\"InnovationM Admin\" \/>\n\t<meta name=\"twitter:label2\" content=\"Est. reading time\" \/>\n\t<meta name=\"twitter:data2\" content=\"11 minutes\" \/>\n<script type=\"application\/ld+json\" class=\"yoast-schema-graph\">{\"@context\":\"https:\\\/\\\/schema.org\",\"@graph\":[{\"@type\":\"Article\",\"@id\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/handling-dynamic-views-in-table-view-cell\\\/#article\",\"isPartOf\":{\"@id\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/handling-dynamic-views-in-table-view-cell\\\/\"},\"author\":{\"name\":\"InnovationM Admin\",\"@id\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/#\\\/schema\\\/person\\\/a831bf4602d69d1fa452e3de0c8862ed\"},\"headline\":\"Handling Dynamic Views in Table View Cell\",\"datePublished\":\"2017-04-04T09:40:24+00:00\",\"mainEntityOfPage\":{\"@id\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/handling-dynamic-views-in-table-view-cell\\\/\"},\"wordCount\":941,\"commentCount\":0,\"image\":{\"@id\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/handling-dynamic-views-in-table-view-cell\\\/#primaryimage\"},\"thumbnailUrl\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/wp-content\\\/uploads\\\/2017\\\/02\\\/Dynamic-Table-View-Cell.png\",\"keywords\":[\"iOS\",\"iPad\",\"iPhone\",\"Mobile\",\"Swift 3.0\",\"UI Design\"],\"articleSection\":[\"iOS\",\"Mobile\"],\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"CommentAction\",\"name\":\"Comment\",\"target\":[\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/handling-dynamic-views-in-table-view-cell\\\/#respond\"]}]},{\"@type\":\"WebPage\",\"@id\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/handling-dynamic-views-in-table-view-cell\\\/\",\"url\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/handling-dynamic-views-in-table-view-cell\\\/\",\"name\":\"Handling Dynamic Views in Table View Cell | InnovationM Blog\",\"isPartOf\":{\"@id\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/#website\"},\"primaryImageOfPage\":{\"@id\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/handling-dynamic-views-in-table-view-cell\\\/#primaryimage\"},\"image\":{\"@id\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/handling-dynamic-views-in-table-view-cell\\\/#primaryimage\"},\"thumbnailUrl\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/wp-content\\\/uploads\\\/2017\\\/02\\\/Dynamic-Table-View-Cell.png\",\"datePublished\":\"2017-04-04T09:40:24+00:00\",\"author\":{\"@id\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/#\\\/schema\\\/person\\\/a831bf4602d69d1fa452e3de0c8862ed\"},\"description\":\"In this post we will see how we can make use of Table View in iOS to create an user interface in which each cell of TableView can have multiple options.\",\"breadcrumb\":{\"@id\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/handling-dynamic-views-in-table-view-cell\\\/#breadcrumb\"},\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"ReadAction\",\"target\":[\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/handling-dynamic-views-in-table-view-cell\\\/\"]}]},{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/handling-dynamic-views-in-table-view-cell\\\/#primaryimage\",\"url\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/wp-content\\\/uploads\\\/2017\\\/02\\\/Dynamic-Table-View-Cell.png\",\"contentUrl\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/wp-content\\\/uploads\\\/2017\\\/02\\\/Dynamic-Table-View-Cell.png\",\"width\":624,\"height\":347},{\"@type\":\"BreadcrumbList\",\"@id\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/handling-dynamic-views-in-table-view-cell\\\/#breadcrumb\",\"itemListElement\":[{\"@type\":\"ListItem\",\"position\":1,\"name\":\"Home\",\"item\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/\"},{\"@type\":\"ListItem\",\"position\":2,\"name\":\"Handling Dynamic Views in Table View Cell\"}]},{\"@type\":\"WebSite\",\"@id\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/#website\",\"url\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/\",\"name\":\"InnovationM - Blog\",\"description\":\"\",\"potentialAction\":[{\"@type\":\"SearchAction\",\"target\":{\"@type\":\"EntryPoint\",\"urlTemplate\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/?s={search_term_string}\"},\"query-input\":{\"@type\":\"PropertyValueSpecification\",\"valueRequired\":true,\"valueName\":\"search_term_string\"}}],\"inLanguage\":\"en-US\"},{\"@type\":\"Person\",\"@id\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/#\\\/schema\\\/person\\\/a831bf4602d69d1fa452e3de0c8862ed\",\"name\":\"InnovationM Admin\",\"image\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/5c99d9eece9dfbc82297cf34ddd58e9fe05bb52fe66c8f6bf6c0a45bfb6d7629?s=96&r=g\",\"url\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/5c99d9eece9dfbc82297cf34ddd58e9fe05bb52fe66c8f6bf6c0a45bfb6d7629?s=96&r=g\",\"contentUrl\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/5c99d9eece9dfbc82297cf34ddd58e9fe05bb52fe66c8f6bf6c0a45bfb6d7629?s=96&r=g\",\"caption\":\"InnovationM Admin\"},\"sameAs\":[\"http:\\\/\\\/www.innovationm.com\\\/\"],\"url\":\"https:\\\/\\\/www.innovationm.com\\\/blog\\\/author\\\/innovationmadmin\\\/\"}]}<\/script>\n<!-- \/ Yoast SEO plugin. -->","yoast_head_json":{"title":"Handling Dynamic Views in Table View Cell | InnovationM Blog","description":"In this post we will see how we can make use of Table View in iOS to create an user interface in which each cell of TableView can have multiple options.","robots":{"index":"index","follow":"follow","max-snippet":"max-snippet:-1","max-image-preview":"max-image-preview:large","max-video-preview":"max-video-preview:-1"},"canonical":"https:\/\/www.innovationm.com\/blog\/handling-dynamic-views-in-table-view-cell\/","og_locale":"en_US","og_type":"article","og_title":"Handling Dynamic Views in Table View Cell | InnovationM Blog","og_description":"In this post we will see how we can make use of Table View in iOS to create an user interface in which each cell of TableView can have multiple options.","og_url":"https:\/\/www.innovationm.com\/blog\/handling-dynamic-views-in-table-view-cell\/","og_site_name":"InnovationM - Blog","article_published_time":"2017-04-04T09:40:24+00:00","og_image":[{"width":624,"height":347,"url":"https:\/\/www.innovationm.com\/blog\/wp-content\/uploads\/2017\/02\/Dynamic-Table-View-Cell.png","type":"image\/png"}],"author":"InnovationM Admin","twitter_misc":{"Written by":"InnovationM Admin","Est. reading time":"11 minutes"},"schema":{"@context":"https:\/\/schema.org","@graph":[{"@type":"Article","@id":"https:\/\/www.innovationm.com\/blog\/handling-dynamic-views-in-table-view-cell\/#article","isPartOf":{"@id":"https:\/\/www.innovationm.com\/blog\/handling-dynamic-views-in-table-view-cell\/"},"author":{"name":"InnovationM Admin","@id":"https:\/\/www.innovationm.com\/blog\/#\/schema\/person\/a831bf4602d69d1fa452e3de0c8862ed"},"headline":"Handling Dynamic Views in Table View Cell","datePublished":"2017-04-04T09:40:24+00:00","mainEntityOfPage":{"@id":"https:\/\/www.innovationm.com\/blog\/handling-dynamic-views-in-table-view-cell\/"},"wordCount":941,"commentCount":0,"image":{"@id":"https:\/\/www.innovationm.com\/blog\/handling-dynamic-views-in-table-view-cell\/#primaryimage"},"thumbnailUrl":"https:\/\/www.innovationm.com\/blog\/wp-content\/uploads\/2017\/02\/Dynamic-Table-View-Cell.png","keywords":["iOS","iPad","iPhone","Mobile","Swift 3.0","UI Design"],"articleSection":["iOS","Mobile"],"inLanguage":"en-US","potentialAction":[{"@type":"CommentAction","name":"Comment","target":["https:\/\/www.innovationm.com\/blog\/handling-dynamic-views-in-table-view-cell\/#respond"]}]},{"@type":"WebPage","@id":"https:\/\/www.innovationm.com\/blog\/handling-dynamic-views-in-table-view-cell\/","url":"https:\/\/www.innovationm.com\/blog\/handling-dynamic-views-in-table-view-cell\/","name":"Handling Dynamic Views in Table View Cell | InnovationM Blog","isPartOf":{"@id":"https:\/\/www.innovationm.com\/blog\/#website"},"primaryImageOfPage":{"@id":"https:\/\/www.innovationm.com\/blog\/handling-dynamic-views-in-table-view-cell\/#primaryimage"},"image":{"@id":"https:\/\/www.innovationm.com\/blog\/handling-dynamic-views-in-table-view-cell\/#primaryimage"},"thumbnailUrl":"https:\/\/www.innovationm.com\/blog\/wp-content\/uploads\/2017\/02\/Dynamic-Table-View-Cell.png","datePublished":"2017-04-04T09:40:24+00:00","author":{"@id":"https:\/\/www.innovationm.com\/blog\/#\/schema\/person\/a831bf4602d69d1fa452e3de0c8862ed"},"description":"In this post we will see how we can make use of Table View in iOS to create an user interface in which each cell of TableView can have multiple options.","breadcrumb":{"@id":"https:\/\/www.innovationm.com\/blog\/handling-dynamic-views-in-table-view-cell\/#breadcrumb"},"inLanguage":"en-US","potentialAction":[{"@type":"ReadAction","target":["https:\/\/www.innovationm.com\/blog\/handling-dynamic-views-in-table-view-cell\/"]}]},{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/www.innovationm.com\/blog\/handling-dynamic-views-in-table-view-cell\/#primaryimage","url":"https:\/\/www.innovationm.com\/blog\/wp-content\/uploads\/2017\/02\/Dynamic-Table-View-Cell.png","contentUrl":"https:\/\/www.innovationm.com\/blog\/wp-content\/uploads\/2017\/02\/Dynamic-Table-View-Cell.png","width":624,"height":347},{"@type":"BreadcrumbList","@id":"https:\/\/www.innovationm.com\/blog\/handling-dynamic-views-in-table-view-cell\/#breadcrumb","itemListElement":[{"@type":"ListItem","position":1,"name":"Home","item":"https:\/\/www.innovationm.com\/blog\/"},{"@type":"ListItem","position":2,"name":"Handling Dynamic Views in Table View Cell"}]},{"@type":"WebSite","@id":"https:\/\/www.innovationm.com\/blog\/#website","url":"https:\/\/www.innovationm.com\/blog\/","name":"InnovationM - Blog","description":"","potentialAction":[{"@type":"SearchAction","target":{"@type":"EntryPoint","urlTemplate":"https:\/\/www.innovationm.com\/blog\/?s={search_term_string}"},"query-input":{"@type":"PropertyValueSpecification","valueRequired":true,"valueName":"search_term_string"}}],"inLanguage":"en-US"},{"@type":"Person","@id":"https:\/\/www.innovationm.com\/blog\/#\/schema\/person\/a831bf4602d69d1fa452e3de0c8862ed","name":"InnovationM Admin","image":{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/secure.gravatar.com\/avatar\/5c99d9eece9dfbc82297cf34ddd58e9fe05bb52fe66c8f6bf6c0a45bfb6d7629?s=96&r=g","url":"https:\/\/secure.gravatar.com\/avatar\/5c99d9eece9dfbc82297cf34ddd58e9fe05bb52fe66c8f6bf6c0a45bfb6d7629?s=96&r=g","contentUrl":"https:\/\/secure.gravatar.com\/avatar\/5c99d9eece9dfbc82297cf34ddd58e9fe05bb52fe66c8f6bf6c0a45bfb6d7629?s=96&r=g","caption":"InnovationM Admin"},"sameAs":["http:\/\/www.innovationm.com\/"],"url":"https:\/\/www.innovationm.com\/blog\/author\/innovationmadmin\/"}]}},"_links":{"self":[{"href":"https:\/\/www.innovationm.com\/blog\/wp-json\/wp\/v2\/posts\/2399","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.innovationm.com\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.innovationm.com\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.innovationm.com\/blog\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/www.innovationm.com\/blog\/wp-json\/wp\/v2\/comments?post=2399"}],"version-history":[{"count":0,"href":"https:\/\/www.innovationm.com\/blog\/wp-json\/wp\/v2\/posts\/2399\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/www.innovationm.com\/blog\/wp-json\/wp\/v2\/media\/2995"}],"wp:attachment":[{"href":"https:\/\/www.innovationm.com\/blog\/wp-json\/wp\/v2\/media?parent=2399"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.innovationm.com\/blog\/wp-json\/wp\/v2\/categories?post=2399"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.innovationm.com\/blog\/wp-json\/wp\/v2\/tags?post=2399"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}