title: How to customise cell in FSCalendar?
body: <p>I am trying to achieve Date Range selection using FSCalendar , and i am achieving that but the view i want that is not proper . so can anyone help for that ? I want output like below screenshot , but i am getting right now like this </p>
  
  <p>My Current Output:</p>
  
  <p><a href="https://i.stack.imgur.com/BjbOI.png" rel="noreferrer"><img src="https://i.stack.imgur.com/BjbOI.png" alt="enter image description here"></a></p>
  
  <p>Desired output:</p>
  
  <p><a href="https://i.stack.imgur.com/vFp2U.png" rel="noreferrer"><img src="https://i.stack.imgur.com/vFp2U.png" alt=" "></a></p>
  
  <p>Viewcontroller.swift</p>
  
  <pre><code>class ViewController: UIViewController {
  
  
      @IBOutlet weak var calendar: FSCalendar!
  
      var firstDate: Date?
      var lastDate: Date?
      var datesRange: [Date]?
      fileprivate let gregorian = Calendar(identifier: .gregorian)
      fileprivate let formatter: DateFormatter = {
          let formatter = DateFormatter()
          formatter.dateFormat = "yyyy-MM-dd"
          return formatter
      }()
      let highlightedColorForRange = UIColor.init(red: 2/255, green: 138/255, blue: 75/238, alpha: 0.2)
  
  
      override func viewDidLoad() {
          super.viewDidLoad()
  
          calendar.delegate = self
          calendar.dataSource = self
          calendar.today = nil
          calendar.calendarHeaderView.backgroundColor = UIColor.lightGray
          calendar.calendarWeekdayView.backgroundColor = UIColor.lightGray.withAlphaComponent(0.1)
          calendar.register(DIYCalendarCell.self, forCellReuseIdentifier: "cell")
          calendar.allowsMultipleSelection = true
          calendar.clipsToBounds = true
      }
  }
  
  extension ViewController {
  
      func configureVisibleCells() {
          self.calendar.visibleCells().forEach { (cell) in
              let date = self.calendar.date(for: cell)
              let position = self.calendar.monthPosition(for: cell)
              self.configureCell(cell, for: date, at: position)
          }
      }
  
      func configureCell(_ cell: FSCalendarCell?, for date: Date?, at position: FSCalendarMonthPosition) {
          let diyCell = (cell as! DIYCalendarCell)
          // Configure selection layer
          if position == .current {
  
              var selectionType = SelectionType.none
  
              if calendar.selectedDates.contains(date!) {
                  let previousDate = self.gregorian.date(byAdding: .day, value: -1, to: date!)!
                  let nextDate = self.gregorian.date(byAdding: .day, value: 1, to: date!)!
                  if calendar.selectedDates.contains(date!) {
                      if calendar.selectedDates.contains(previousDate) &amp;&amp; calendar.selectedDates.contains(nextDate) {
                          diyCell.selectionLayer.fillColor = highlightedColorForRange.cgColor
                          selectionType = .middle
                      }
                      else if calendar.selectedDates.contains(previousDate) &amp;&amp; calendar.selectedDates.contains(date!) {
                          selectionType = .single // .rightBorder
                      }
                      else if calendar.selectedDates.contains(nextDate) {
                          selectionType = .single // .leftBorder
                      }
                      else {
                          selectionType = .middle //.single
                      }
                  }
              }
              else {
                  selectionType = .none
              }
              if selectionType == .none {
                  diyCell.selectionLayer.isHidden = true
                  return
              }
              diyCell.selectionLayer.isHidden = false
              diyCell.selectionType = selectionType
  
          } else {
              diyCell.selectionLayer.isHidden = true
          }
      }
  
      func datesRange(from: Date, to: Date) -&gt; [Date] {
          // in case of the "from" date is more than "to" date,
          // it should returns an empty array:
          if from &gt; to { return [Date]() }
  
          var tempDate = from
          var array = [tempDate]
  
          while tempDate &lt; to {
              tempDate = Calendar.current.date(byAdding: .day, value: 1, to: tempDate)!
              array.append(tempDate)
          }
  
          return array
      }
  
  }
  
  extension ViewController:FSCalendarDelegate,FSCalendarDataSource,FSCalendarDelegateAppearance {
  
      func calendar(_ calendar: FSCalendar, boundingRectWillChange bounds: CGRect, animated: Bool) {
          self.calendar.frame.size.height = bounds.height
      }
  
      func calendar(_ calendar: FSCalendar, didSelect date: Date, at monthPosition: FSCalendarMonthPosition) {
          // nothing selected:
          if firstDate == nil {
              firstDate = date
              datesRange = [firstDate!]
              print("datesRange contains: \(datesRange!)")
               configureVisibleCells()
              return
          }
  
          // only first date is selected:
          if firstDate != nil &amp;&amp; lastDate == nil {
              // handle the case of if the last date is less than the first date:
              if date &lt;= firstDate! {
                  calendar.deselect(firstDate!)
                  firstDate = date
                  datesRange = [firstDate!]
  
                  print("datesRange contains: \(datesRange!)")
                  configureVisibleCells()
                  return
              }
  
              let range = datesRange(from: firstDate!, to: date)
  
              lastDate = range.last
  
              for d in range {
                  calendar.select(d)
              }
  
              datesRange = range
  
              print("datesRange contains: \(datesRange!)")
              configureVisibleCells()
              return
          }
  
          // both are selected:
          if firstDate != nil &amp;&amp; lastDate != nil {
              for d in calendar.selectedDates {
                  calendar.deselect(d)
              }
  
              lastDate = nil
              firstDate = nil
  
              datesRange = []
  
              print("datesRange contains: \(datesRange!)")
          }
          configureVisibleCells()
      }
  
      func calendarCurrentPageDidChange(_ calendar: FSCalendar) {
  
      }
  
      func calendar(_ calendar: FSCalendar, cellFor date: Date, at position: FSCalendarMonthPosition) -&gt; FSCalendarCell {
          let cell = calendar.dequeueReusableCell(withIdentifier: "cell", for: date, at: position)
          return cell
      }
  
      func calendar(_ calendar: FSCalendar, willDisplay cell: FSCalendarCell, for date: Date, at monthPosition: FSCalendarMonthPosition) {
          self.configureCell(cell, for: date, at: monthPosition)
      }
  
      func calendar(_ calendar: FSCalendar, shouldSelect date: Date, at monthPosition: FSCalendarMonthPosition) -&gt; Bool {
          return monthPosition == FSCalendarMonthPosition.current
      }
  
      func calendar(_ calendar: FSCalendar, shouldDeselect date: Date, at monthPosition: FSCalendarMonthPosition) -&gt; Bool {
          return false
      }
  
      func calendar(_ calendar: FSCalendar, didDeselect date: Date, at monthPosition: FSCalendarMonthPosition) {
          print("did deselect date \(self.formatter.string(from: date))")
          configureVisibleCells()
      }
  
  }  
  </code></pre>
  
  <p>DIYCalendarCell.swift</p>
  
  <pre><code>public var selectedColor = UIColor.init(red: 2/255, green: 138/255, blue: 75/255, alpha: 1)
  
  enum SelectionType : Int {
      case none
      case single
      case leftBorder
      case middle
      case rightBorder
  }
  class DIYCalendarCell: FSCalendarCell {
  
      weak var circleImageView: UIImageView!
      weak var selectionLayer: CAShapeLayer!
  
      var selectionType: SelectionType = .none {
          didSet {
              setNeedsLayout()
          }
      }
  
      required init!(coder aDecoder: NSCoder!) {
          fatalError("init(coder:) has not been implemented")
      }
  
      override init(frame: CGRect) {
          super.init(frame: frame)
  
          let selectionLayer = CAShapeLayer()
          selectionLayer.fillColor = selectedColor.cgColor
          selectionLayer.actions = ["hidden": NSNull()]
          self.contentView.layer.insertSublayer(selectionLayer, below: self.titleLabel!.layer)
          self.selectionLayer = selectionLayer
  
          self.shapeLayer.isHidden = true
          let view = UIView(frame: self.bounds)
          self.backgroundView = view;
  
      }
  
      override func layoutSubviews() {
          super.layoutSubviews()
         // self.circleImageView.frame = self.contentView.bounds
          self.backgroundView?.frame = self.bounds.insetBy(dx: 1, dy: 1)
          self.selectionLayer.frame = self.contentView.bounds
  
          if selectionType == .middle {
              self.selectionLayer.path = UIBezierPath(rect: self.selectionLayer.bounds).cgPath
          }
          else if selectionType == .leftBorder {
              self.selectionLayer.path = UIBezierPath(roundedRect: self.selectionLayer.bounds, byRoundingCorners: [.topLeft, .bottomLeft], cornerRadii: CGSize(width: self.selectionLayer.frame.width / 2, height: self.selectionLayer.frame.width / 2)).cgPath
          }
          else if selectionType == .rightBorder {
              self.selectionLayer.path = UIBezierPath(roundedRect: self.selectionLayer.bounds, byRoundingCorners: [.topRight, .bottomRight], cornerRadii: CGSize(width: self.selectionLayer.frame.width / 2, height: self.selectionLayer.frame.width / 2)).cgPath
          }
          else if selectionType == .single {
              let diameter: CGFloat = min(self.selectionLayer.frame.height, self.selectionLayer.frame.width)
              self.selectionLayer.path = UIBezierPath(ovalIn: CGRect(x: self.contentView.frame.width / 2 - diameter / 2, y: self.contentView.frame.height / 2 - diameter / 2, width: diameter, height: diameter)).cgPath
          }
      }
  
      override func configureAppearance() {
          super.configureAppearance()
          // Override the build-in appearance configuration
          if self.isPlaceholder {
              self.eventIndicator.isHidden = true
              self.titleLabel.textColor = UIColor.lightGray
          }
      }
  
  }
  </code></pre>