堆叠两个UITableViews

时间:2016-03-05 20:14:14

标签: ios uitableview

我在应用程序的多个屏幕中使用UITableViewUITableViewController

我最近与我所在组织的产品团队进行了交谈,并且他们要求在其中一个屏幕中,我预先设置了大约15个外观和功能非常不同的单元格。

在谷歌搜索后,似乎唯一的方法是使每个实现的UITableViewDelegate方法复杂化如下:

if section == 0 {
    ...
}
if section == 1 {
    ...
}

我不想这样做,因为显示此表的其他屏幕不需要这种逻辑,突然可重用性变得更加复杂。

理想情况,我想要的是垂直堆叠两个表格视图,以便一个附加到另一个的底部。

我的架构有问题,或者在IOS中没有这么好的方法吗?

2 个答案:

答案 0 :(得分:3)

我必须在几个不同的时间做类似的事情,这就是我留下的东西:

  1. 根据部分添加特殊情况。令人惊讶的是,我发现这是最容易阅读和维护的。只需使用静态和清除变量名称而不是if (section == 0)

  2. 为包含表视图的第0行创建一个特殊单元格。这不是最简单的事情,但它可以很好地工作,能够将您的代码分解为多个文件,这些文件通常可以更好地进行维护。当您对委托方法进行排序时,这确实会变得很痛苦,但是一旦解决了这个问题,那么它就是一个非常动态的解决方案。

  3. 如果您没有使用标题,请执行与#2相同的操作,但请根据您的特殊情况使用标题。当规范发生变化时,这很有效(如果可用),因为您可以将视图放在不同的页眉或页脚中。

  4. 将两个表视图放在某种容器视图中。我试过这个,它不漂亮。我不推荐。

  5. 将两个表添加到另一个表中。这可以用来分割细胞来自哪里。这样做,你可以继承UITableView并创建一个标志来将特殊表添加到表中。这不是推荐和起点的解决方案。

  6. 无论您选择哪种方式,请确保其清晰易读。当你没有低头时,UITableView会变得复杂。

答案 1 :(得分:0)

@Fennelouski,非常感谢你的提示,我实际上最终选择了你未经推荐的选项#4:

  

将两个表视图放在容器视图中

我走向这个方向的主要原因是因为在过去,当试图将滚动视图放在其他滚动视图中时,我发现了有关弹跳的意外行为。即使我在嵌套滚动视图上将bounces设置为false,我发现当使用嵌套滚动视图开始拖动时,父滚动视图也不会移动,而不是在它的内容结尾处。

我的解决方案最终并不可怕(部分原因是我的应用程序是使用我设计的框架构建的,这允许非常棒的事件)。我在这里概述一下:

  1. 将两个表firstsecond添加到由UIViewController container控制的UIView controller
  2. 将两个表的大小设置为container的大小。
  3. first.contentInset.bottom设置为second.contentSize.height并将second.contentInset.top设置为first.contentSize.height(必须这样做才能让一张桌子足够轻弹,以便击中另一张桌子的末端表..并且必须在任何一个表中改变高度时再次完成)
  4. second.backgroundColor设为clear
  5. second的最新方法pointInside:withEvent:定义为return point.y > 0(已完成,因此second上方空白区域的触摸事件将转换为first
  6. 当调用任何一个表的委托方法scrollViewWillBeginDragging:时,存储哪个表开始拖动(我使用了一个名为last_dragged的属性)。
  7. 当调用表格的委托方法scrollViewDidScroll:时,根据偏移量定位 last_dragged的表格 last_dragged
  8. 的表格

    这是我用于controller的代码(是的,是用 ruby​​ 编写的,但希望你能够以sudo代码的形式阅读它)

    def load_view
      content.add_subview first, size: content.size
      content.add_subview second, size: content.size
      set_content_offsets
      listen_for_events
      set_second_y
    end
    
    def set_content_offsets
      first.content_inset_bottom = second.content_size_height
      second.content_inset_top = first.content_size_height
    end
    
    def listen_for_events
      listen_to_first
      listen_to_second
    end
    
    def listen_to_first
      first.on('refresh', method(:set_content_offsets))
      first.on('begin_drag', method(:second_dragged))
      first.on('scroll', method(:scroll))
    end
    
    def listen_to_second
      second.on('refresh', method(:set_content_offsets))
      second.on('begin_drag', method(:second_dragged))
      second.on('scroll', method(:scroll))
    end
    
    def first_dragged
      @last_dragged = :first
    end
    
    def second_dragged
      @last_dragged = :second
    end
    
    def scroll
      if @last_dragged == :first
        set_second_y
      else
        set_first_y
      end
    end
    
    def set_first_y
      first.content_offset_y =
        first.content_size_height +
        second.content_offset_y
    end
    
    def set_second_y
      second.content_offset_y =
        first.content_offset_y -
        first.content_size_height
    end