2016-08-29 7 views
0

Я пытаюсь использовать IBInspectable, чтобы добавить границы к моим представлениям.EXC_BAD_ACCESS Использование IBInspectable

extension UIView { 

    private func getBorder(integer: Int) -> UIRectEdge { 
     if integer == 1 { 
      return .top 
     } else if integer == 2 { 
      return .left 
     } else if integer == 3 { 
      return .right 
     } else if integer == 4 { 
      return .bottom 
     } 
     return .all 

    } 

    @IBInspectable var border: Int? { 
     get { 
      return self.border 
     } 
     set (value) { 
      self.border = value 
      for v in addBorder(edges: self.getBorder(integer: self.border!)) { 
       self.addSubview(v) 
      } 
     } 
    } 

    @IBInspectable var borderColor: UIColor? { 
     get { 
      return self.borderColor 
     } 
     set (value) { 
      self.borderColor = value //EXC_BAD_ACCESS here 
      for v in addBorder(edges: self.getBorder(integer: self.border!), color: borderColor!) { 
       self.addSubview(v) 
      } 
     } 
    } 

    private func addBorder(edges: UIRectEdge, color: UIColor = UIColor.white, thickness: CGFloat = 1) -> [UIView] { 
     ... 
    } 
} 

Катастрофа происходит на линии self.borderColor = valueset для borderColor).

Все, что он говорит в журнале отладки, - (lldb). Сама авария говорит:

Тема 1: EXC_BAD_ACCESS (код = 2, адрес = 0x7fff53cc5fe8)

Вот моя Раскадровка:

storyboard

Как я могу решить эту проблему ? Благодаря!

ответ

1

У вас там бесконечная рекурсия, которая вызывает крушение. В основном внутри сеттера borderColor вы вызываете сеттер для того же свойства, что приводит к бесконечной рекурсии.

Это происходит из-за того, что расширениям классов не разрешено хранить сохраненные свойства, поэтому Swift не создает резервный сервер для вашего свойства, вместо этого он рассматривает его как вычисленное свойство и вызывает setter при попытке установить свойство.

Есть два решения, которые я могу думать в это время, что решит вашу проблему:

  1. Подкласса UIView, добавьте два свойства там, обновляет класс в IB, чтобы соответствовать имени вашего нового класс.
  2. Использование связанных объектов в ваших аксессуарах UIView (objc_setAssociatedObject()/objc_getAssociatedObject()) вместо прямого справочника iVar. Вам не нужно подклассы и обновлять xib, но это решение немного грязнее первого.
Смежные вопросы