iOS : The goal is to put an image over a UITableView, the UITableView works normally.
Generally, put an image over a UITableView, the touch events of the UITableView is cut off.
Here is the scene, there is a piano score app. The music notes line by line is shown by a UITableView.
Then user could put a canvas over the notes list, they could draw over the score.
I need to put the custom drawing over the piano score UITableView, and the UITableView works normally.
Here is my idea:
put the drawing View on the tableView, underneath the cells.
Each cell have a reference of the drawing View.
Each cell also have a canvas slice view on its top.
The key method is CALayer
's open func render(in ctx: CGContext)
Here is the relevant code:
class RenderV: UIView {
var renderer: UIView?
var index = -1
override func draw(_ rect: CGRect) {
guard let context = UIGraphicsGetCurrentContext()
else { return }
var f: CGSize = .zero
if let v = renderer{
f = v.frame.size
}
let w = frame.size.width
let h = frame.size.height
context.translateBy(x: w/2 - f.width/2, y: h * CGFloat(index) - f.height)
renderer?.layer.render(in: context)
}
}
canvas used in UITableViewCell:
class TableViewCell: UITableViewCell {
var renderer: UIView?{
didSet{
guard idx > 0 else {
return
}
contain.index = idx
contain.renderer = renderer
contain.setNeedsDisplay()
}
}
@IBOutlet weak var contain: RenderV!
var idx = -1
}
Call code:
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
let cel = tableView.dequeueReusableCell(withIdentifier: "TableViewCell", for: indexPath) as! TableViewCell
cel.idx = 6 - indexPath.row
cel.renderer = img
return cel
}
My solution is not intuitive, and needs calculating.
Any better idea?
Here is an easy demo effect:
I'm not sure that I understand completely what is the problem. What I understand is that the view that you render over the UITableView
is blocking the touch events that you want to be passed to the table, right?
If it's the case, just set the view's isUserInteractionEnabled = false
. That will enable the events to penetrate the view and be captured by the UITableView
.