Vah.Sah
Vah.Sah

Reputation: 532

UITableViewRowAction with image, swift

In my app I would like to use UITableViewRowAction with image instead of title text. I set background image using:

let edit = UITableViewRowAction(style: .Normal, title: "Edit") { action, index in
  self.indexPath = indexPath
  self.performSegueWithIdentifier("toEdit", sender: self)
}
edit.backgroundColor = UIColor(patternImage: UIImage(named: "edit")!)

However image appears many times.

enter image description here

How can I fix this to have only one image in row?

Upvotes: 2

Views: 1920

Answers (2)

a_tuo
a_tuo

Reputation: 659

I have wrote a subclass of UITableViewRowAction to help you calculating the length of the title and you just pass the size of rowAction and the image.

class CustomRowAction: UITableViewRowAction {

    init(size: CGSize, image: UIImage, bgColor: UIColor) {
        super.init()

        // calculate actual size & set title with spaces
        let defaultTextPadding: CGFloat = 15  
        let defaultAttributes = [ NSFontAttributeName: UIFont.systemFont(ofSize: 18)]   // system default rowAction text font
        let oneSpaceWidth = NSString(string: " ").size(attributes: defaultAttributes).width
        let titleWidth = size.width - defaultTextPadding * 2
        let numOfSpace = Int(ceil(titleWidth / oneSpaceWidth))

        let placeHolder = String(repeating: " ", count: numOfSpace)
        let newWidth = (placeHolder as NSString).size(attributes: defaultAttributes).width + defaultTextPadding * 2
        let newSize = CGSize(width: newWidth, height: size.height)

        title = placeHolder

        // set background with pattern image

        UIGraphicsBeginImageContextWithOptions(newSize, false, UIScreen.main.nativeScale)

        let context = UIGraphicsGetCurrentContext()!
        context.setFillColor(bgColor.cgColor)
        context.fill(CGRect(origin: .zero, size: newSize))

        let originX = (newWidth - image.size.width) / 2
        let originY = (size.height - image.size.height) / 2
        image.draw(in: CGRect(x: originX, y: originY, width: image.size.width, height: image.size.height))
        let patternImage = UIGraphicsGetImageFromCurrentImageContext()!

        UIGraphicsEndImageContext()

        backgroundColor = UIColor(patternImage: patternImage)
    }
}

You can see my project: CustomSwipeCell for more detail.

Upvotes: 0

smukamuka
smukamuka

Reputation: 1537

The problem is that the image used as pattern won't fit the space, It will be repeated in order to fill it. One option to have a non-repeated image is to

  • use a UITableViewCell with fixed height
  • use image that fits that height

Upvotes: 1

Related Questions