喉咙里 發表於 2022-11-22 09:18:30

iOS开发学习TableView展现一个list实例

<div id="navCategory"><h5 class="catalogue">目录</h5><ul class="first_class_ul"><li>TableView 基础</li><ul class="second_class_ul"><li>TableView用来做什么</li></ul><li>如何写一个最简单的TableView</li><ul class="second_class_ul"></ul><li>拆解版TableView</li><ul class="second_class_ul"><li>Delegate &amp; DataSource</li><li>继承UIViewController</li><li>自己的Cell class</li></ul><li>补充知识: Delegation</li><ul class="second_class_ul"></ul></ul></div><p class="maodian"></p><h2>TableView 基础</h2>
<p>本文讲讲TableView的基本使用. 顺便介绍一下delegation.</p>
<p class="maodian"></p><h3>TableView用来做什么</h3>
<p>TableView用来展示一个很长的list. 和Android中的RecyclerView不同, iOS中的TableView只能是竖直方向的list.</p>
<div class="cros igoods"><div class="goodsin" data-img="https://img14.360buyimg.com/pop/jfs/t25411/112/1300556906/185016/6f29ec4b/5badc240Nec491c62.jpg" data-name="Android进阶解密(博文视点出品)" data-owner="京东自营" data-price="98.8" data-tgid="38" data-url="https://union-click.jd.com/jdc?e=&amp;p=JF8BAMoJK1olXwUCVFxaDE4XBV8IGF4XVAACVm4ZVxNJXF9RXh5UHw0cSgYYXBcIWDoXSQVJQwYBUVxUDksVHDZNRwYlNnwEPCpdQzVyfWwLREVRCn1hKAEoaEcbM2gNHF4dXwMBZF5eDkwXAmoIK2sVXDZQOobrvpOysnPcsdTA1ZEyVW5dD0wfAmkAE1sVWgEEZF5VDHtUVypcWBhdbTYyV25tOEsnAF9WdVpGVQYDVgtVZhZHQDQKGF1MMwQHVFdYCU4SBF8KGloXXzYy"></div></div>
<p class="maodian"></p><h2>如何写一个最简单的TableView</h2>
<p>一个最简单的TableViewController看起来像这样:</p>
<div class="jb51code"><pre class="brush:cpp;">class ViewController: UITableViewController {
    var data: = []
    override func viewDidLoad() {
      super.viewDidLoad()
      // Do any additional setup after loading the view.
      // loadData()
      print(data)
    }
    override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -&gt; Int {
      data.count
    }
    override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -&gt; UITableViewCell {
      let cell = tableView.dequeueReusableCell(withIdentifier: "MyCell", for: indexPath)
      cell.textLabel?.text = data
      return cell
    }
}
</pre></div>
<p>这里data是想展示的数据类型, 可以hardcode一些数据.</p>
<p>这么简单是因为这个ViewController继承了<code>UITableViewController</code>, 并且cell的部分使用了storyboard.</p>
<p>这里需要用<code>dequeueReusableCell</code>方法, 是为了cell的复用, 因为list内容很多的时候cell view是可以循环使用的. (很像Android里的RecyclerView).</p>
<p><code>UITableViewController</code>的签名是这样:</p>
<div class="jb51code"><pre class="brush:cpp;">open class UITableViewController : UIViewController, UITableViewDelegate, UITableViewDataSource {
</pre></div>
<p>它为我们做了以下三件事:</p>
<ul><li>设置view为一个<code>UITableView</code>.</li><li>设置<code>delegate=self</code>.</li><li>设置<code>dataSource=self</code>.</li></ul>
<p>这种方式的局限性在于第一点, 它的根view是一个TableView, 如果我们的需求比较复杂, 不仅仅是一个demo, 那么可能需要组合View.</p>
<p class="maodian"></p><h2>拆解版TableView</h2>
<p>我们也可以直接继承<code>UIViewController</code>类, 然后自己动手做上面的几条设置.</p>
<p class="maodian"></p><h3>Delegate &amp; DataSource</h3>
<p>TableView有两个重要的方面需要关注:</p>
<ul><li>UITableViewDelegate: 管理和用户的交互, 比如选择, 滑动手势等. 没有必须要实现的方法.</li><li>UITableViewDataSource: 提供和管理数据, 包括了数据对应的cell或者header. 有两个必须要实现的方法(如上面的代码例子所示).</li></ul>
<p class="maodian"></p><h3>继承UIViewController</h3>
<p>继承UIViewController而不是<code>UITableViewController</code>之后, 需要自己写一个tableView并加在view里. 再分别实现<code>UITableViewDelegate</code>和<code>UITableViewDataSource</code>, 这里写在extension里, 拆分完之后set给tableView:</p>
<div class="jb51code"><pre class="brush:cpp;">tableView.delegate = self
tableView.dataSource = self
</pre></div>
<p>整体改造后代码如下:</p>
<div class="jb51code"><pre class="brush:cpp;">class ViewController: UIViewController {
    var data: = ["Hello", "World"]
    private let tableView = UITableView()
    override func loadView() {
      view = UIView()
      view.addSubview(tableView)
      tableView.translatesAutoresizingMaskIntoConstraints = false
      NSLayoutConstraint.activate([
            tableView.topAnchor.constraint(equalTo: view.topAnchor),
            tableView.bottomAnchor.constraint(equalTo: view.bottomAnchor),
            tableView.leadingAnchor.constraint(equalTo: view.leadingAnchor),
            tableView.trailingAnchor.constraint(equalTo: view.trailingAnchor),
      ])
    }
    override func viewDidLoad() {
      super.viewDidLoad()
      tableView.register(MyCell.self, forCellReuseIdentifier: "MyCell")
      tableView.delegate = self
      tableView.dataSource = self
    }
}
extension ViewController: UITableViewDelegate {}
extension ViewController: UITableViewDataSource {
    func tableView(_: UITableView, numberOfRowsInSection _: Int) -&gt; Int {
      data.count
    }
    func tableView(_: UITableView, cellForRowAt indexPath: IndexPath) -&gt; UITableViewCell {
      if let cell = tableView.dequeueReusableCell(withIdentifier: "MyCell", for: indexPath) as? MyCell {
            cell.configure(with: data)
            return cell
      }
      return UITableViewCell()
    }
}
</pre></div>
<p class="maodian"></p><h3>自己的Cell class</h3>
<p>这里Cell也改用代码类, 写一个这样的类:</p>
<div class="jb51code"><pre class="brush:cpp;">class MyCell: UITableViewCell {
    private let label = UILabel()
    override init(style: UITableViewCell.CellStyle, reuseIdentifier: String?) {
      super.init(style: style, reuseIdentifier: reuseIdentifier)
      contentView.addSubview(label)
      label.translatesAutoresizingMaskIntoConstraints = false
      NSLayoutConstraint.activate([
            label.topAnchor.constraint(equalTo: contentView.topAnchor),
            label.bottomAnchor.constraint(equalTo: contentView.bottomAnchor),
            label.leadingAnchor.constraint(equalTo: contentView.leadingAnchor),
            label.trailingAnchor.constraint(equalTo: contentView.trailingAnchor),
      ])
    }
    @available(*, unavailable)
    required init?(coder _: NSCoder) {
      fatalError("init(coder:) has not been implemented")
    }
    func configure(with data: String) {
      label.text = data
    }
}
</pre></div>
<p>注意tableView注册这个Cell类型:</p>
<div class="jb51code"><pre class="brush:cpp;">override func viewDidLoad() {
      super.viewDidLoad()
      tableView.register(MyCell.self, forCellReuseIdentifier: "MyCell")
}
</pre></div>
<p class="maodian"></p><h2>补充知识: Delegation</h2>
<p>上面的方法初看可能会非常怪. 这里还涉及到了一个知识点是iOS中的delegate. 它存在的意义是为了拓展本身类的功能.</p>
<p>Apple自己的很多API就用了delegate protocol, 比如<code>UIApplicationDelegate</code>, <code>UITableViewDelegate</code>. 如果我们想自己定义一个:</p>
<div class="jb51code"><pre class="brush:cpp;">protocol MyTypeDelegate: AnyObject {
    func myType(_ myType: MyType,
                      shouldDoSomething argumentString: String) -&gt; Bool
    func myType(_ myType: MyType,
                      didAbortWithError error: Error)
    func myTypeDidFinish(_ myType: MyType)
}
class MyType {
    weak var delegate: MyTypeDelegate?
}
</pre></div>
<p>定义delegation的几个原则:</p>
<ul><li>方法名以被代理的类型开头.</li><li>方法的第一个参数是被代理的对象.</li></ul>
<p>References</p>
<p>Filling a table with data</p>
<p>Table View Guide</p>
<p>以上就是iOS系列学习TableView展现一个list实例的详细内容,更多关于iOS TableView展现list的资料请关注琼殿技术社区其它相关文章!</p>
                           
                            <div class="art_xg">
                              <b>您可能感兴趣的文章:</b><ul><li>iOS开发TableView网络请求及展示预加载实现示例</li><li>ios开发UITableViewCell图片加载优化详解</li><li>iOS ScrollView嵌套tableView联动滚动的思路与最佳实践</li><li>iOS优化UITableViewCell高度计算的一些事儿</li><li>iOS自定义UITableView实现不同系统下的左滑删除功能详解</li><li>iOS11解决UITableView侧滑删除无限拉伸的方法</li><li>ios UITableView 自定义右滑删除的实现代码</li></ul>
                            </div>

                        </div>
                        <!--endmain-->
頁: [1]
查看完整版本: iOS开发学习TableView展现一个list实例