FSCalendar cell 색상변경이 안되요..

6 답변 글타래를 보이고 있습니다
  • 글쓴이
    • 정재 이
      참가자
      • 글작성 : 4
      • 답글작성 : 11

      현재 캘린더 기능을 구현하고 있는데, DB에 있는 날짜 정보를 읽어와서 해당 날짜들만 색상을 채워주고 싶습니다. 코드는 아래와 같이 구성하였습니다. 캘린더의 셀을 클릭하였을때 작동하는 함수는 잘 작동하는 것을 확인하였습니다.

      import UIKit
      import FSCalendar
      
      class CalendarViewController: UIViewController, FSCalendarDataSource, FSCalendarDelegate, UIGestureRecognizerDelegate{
      
      @IBOutlet weak var calendar: FSCalendar!
      
      @IBOutlet weak var SegmentedControl: UISegmentedControl!
      
      let DB = DataBaseAPI.init()
      let Quary = DataBaseQuery.init()
      
      fileprivate lazy var dateFormatter: DateFormatter = {
      let formatter = DateFormatter()
      formatter.dateFormat = "yyyy-MM-dd"
      return formatter
      }()
      
      fileprivate lazy var scopeGesture: UIPanGestureRecognizer = {
      [unowned self] in
      let panGesture = UIPanGestureRecognizer(target: self.calendar, action: #selector(self.calendar.handleScopeGesture(_:)))
      panGesture.delegate = self
      panGesture.minimumNumberOfTouches = 1
      panGesture.maximumNumberOfTouches = 2
      return panGesture
      }()
      
      var fillDefaultColorsArray : Array<Array<String>> = []
      var fillDefaultColorsDictionary = [String : Int ]()
      
      let SegmentedBarData = ["🟩휴가","🟥훈련","🟨외출","🟦파견", "⬜️삭제"]
      let SegmentedBarColor = [UIColor.green,UIColor.red,UIColor.yellow,UIColor.blue , UIColor.white]
      
      override func viewDidLoad() {
      
      super.viewDidLoad()
      
      //네비게이션바 세팅
      self.navigationItem.hidesBackButton = true;
      self.navigationItem.leftBarButtonItem = nil;
      let navview = Variable_Functions.init()
      self.navigationItem.titleView = navview.navView
      
      
      //세그먼트바 세팅
      SegmentedControl.removeAllSegments()
      SegmentedBarData.map({ text in
      SegmentedControl.insertSegment(withTitle: text, at: SegmentedControl.numberOfSegments, animated: false)
      })
      SegmentedControl.selectedSegmentIndex = 0
      
      
      //DB에서 불러오기
      fillDefaultColorsArray = DB.query(statement: Quary.SelectStar(Tablename: "Calendar"), ColumnNumber: 2)
      fillDefaultColorsArray.map({ each in
      fillDefaultColorsDictionary.updateValue(Int(each[1])! , forKey: each[0])
      })
      print(fillDefaultColorsDictionary)
      
      self.calendar.dataSource = self
      self.calendar.delegate = self
      self.calendar.register(FSCalendarCell.self, forCellReuseIdentifier: "CELL")
      self.calendar.allowsMultipleSelection = true
      self.calendar.swipeToChooseGesture.isEnabled = true
      self.calendar.appearance.caseOptions = [.headerUsesUpperCase,.weekdayUsesSingleUpperCase]
      
      }
      
      func calendar(_ calendar: FSCalendar, cellFor date: Date, at position: FSCalendarMonthPosition) -> FSCalendarCell {
      let cell = calendar.dequeueReusableCell(withIdentifier: "CELL", for: date, at: position)
      cell.imageView.backgroundColor = UIColor.red
      return cell
      }
      
      
      //날짜가 선택되어있을때
      func calendar(_ calendar: FSCalendar, didSelect date: Date, at monthPosition: FSCalendarMonthPosition) {
      let date_string = self.dateFormatter.string(from: date)
      //삭제
      if self.SegmentedControl.selectedSegmentIndex == 4 && fillDefaultColorsDictionary[date_string] != nil {
      if (DB.delete(statement: Quary.Delete(Tablename: "Calendar", Condition: "marked_date = " + "'\(date_string)'"))){
      print("delete success at calander")
      }
      }else{
      //기존 존재한다면 삭제하고 삽입한다.
      if (DB.delete(statement: Quary.Delete(Tablename: "Calendar", Condition: "marked_date = " + "'\(date_string)'"))){
      print("delete success at calander before insert")
      }
      if (DB.insert(statement: Quary.insert(Tablename: "Calendar", Values: " '\(date_string)', \(SegmentedControl.selectedSegmentIndex + 1)" ))){
      print("insert success at calander")
      }
      }
      }
      
      // 스와이프
      func calendarCurrentPageDidChange(_ calendar: FSCalendar) {
      print(calendar)
      }
      
      //골랐을때 색싱 변경
      func calendar(_ calendar: FSCalendar, appearance: FSCalendarAppearance, fillSelectionColorFor date: Date) -> UIColor? {
      return UIColor.white
      }
      
      
      //기본색상
      func calendar(_ calendar: FSCalendar, appearance: FSCalendarAppearance, fillDefaultColorFor date: Date) -> UIColor? {
      return UIColor.red
      let key = self.dateFormatter.string(from: date)
      
      if let colorindex = fillDefaultColorsDictionary[key] {
      return SegmentedBarColor[colorindex-1]
      }else{
      return appearance.borderSelectionColor
      }
      }
      }
      

      그러나, 셀의 색상을 변경하는 함수를 아래와 같이 2가지 방법으로 시도해봤는데 모두 실패하였습니다. 3시간 넘게 고민하였으나, 해결이 안되어 이렇게 자문을 구합니다. 아예 빨간색을 바로 return하도록 하여도, 캘린더의 모든 셀들의 색상이 변하지 않습니다. 도와주십시오….

      func calendar(_ calendar: FSCalendar, cellFor date: Date, at position: FSCalendarMonthPosition) -> FSCalendarCell
      func calendar(_ calendar: FSCalendar, appearance: FSCalendarAppearance, fillDefaultColorFor date: Date) -> UIColor?
      
      
      • 이 게시글은 정재 이에 의해 4 years, 7 months 전에 수정됐습니다.
      • 이 게시글은 정재 이에 의해 4 years, 7 months 전에 수정됐습니다.
    • 정재 이
      참가자
      • 글작성 : 4
      • 답글작성 : 11

      코드를 복사 붙여넣기 하니 들여쓰기가 다 사라졌군요… 가독성이 좋지않더라도 도와주시면 감사하겠습니다…

    • 김수호 김
      참가자
      • 글작성 : 0
      • 답글작성 : 5

      FSCalendarDelegateAppearance 빼먹으셨네요. 추가하시면 아마 될거에요 ~

      • 이 답변은 김수호 김에 의해 4 years, 7 months 전에 수정됐습니다.
    • 정재 이
      참가자
      • 글작성 : 4
      • 답글작성 : 11

      추가하여서 해결하였습니다!!
      그런데 추가적으로 질문이 있습니다…
      1. 코드를 아래와 같이 수정하였습니다. 선택되자마자, 해당 칸의 선택을 deselect하고 데이터를 다시 로드하였습니다. 다시 로드할 때 딕션어리에 들어있는 것을 보면서 로드가 되는데, 딕션어리 안에 기존에 저장되어 있는 값 변경되지는 않는데, 3일을 누르면 12일이 같이 선택되고 있습니다. 특정 날짜를 눌렀을 때 다른 날짜도 같이 선택되는데 왜 이럴까요?

      import UIKit
      import FSCalendar
      
      class CalendarViewController: UIViewController, FSCalendarDataSource, FSCalendarDelegate, FSCalendarDelegateAppearance {
      
          @IBOutlet weak var calendar: FSCalendar!
      
          @IBOutlet weak var SegmentedControl: UISegmentedControl!
      
          let DB = DataBaseAPI.init()
          let Quary = DataBaseQuery.init()
      
          fileprivate lazy var dateFormatter: DateFormatter = {
              let formatter = DateFormatter()
              formatter.dateFormat = "yyyy-MM-dd"
              return formatter
          }()
      
      
          var fillDefaultColorsArray : Array<Array<String>> = []
          var fillDefaultColorsDictionary = [String : Int ]()
      
      
          let SegmentedBarData = ["🟩휴가","🟥훈련","🟨외출","🟦파견", "⬜️삭제"]
          let SegmentedBarColor = [UIColor.green,UIColor.red,UIColor.yellow,UIColor.blue , UIColor.white]
      
          override func viewDidLoad() {
      
              super.viewDidLoad()
      
              //네비게이션바 세팅
              self.navigationItem.hidesBackButton = true;
              self.navigationItem.leftBarButtonItem = nil;
              let navview = Variable_Functions.init()
              self.navigationItem.titleView = navview.navView
      
      
              //세그먼트바 세팅
              SegmentedControl.removeAllSegments()
              SegmentedBarData.map({ text in
                 SegmentedControl.insertSegment(withTitle: text, at: SegmentedControl.numberOfSegments, animated: false)
              })
              SegmentedControl.selectedSegmentIndex = 0
      
      
              //DB에서 불러오기
              fillDefaultColorsArray = DB.query(statement: Quary.SelectStar(Tablename: "Calendar"), ColumnNumber: 2)
              fillDefaultColorsArray.map({ each in
                  fillDefaultColorsDictionary.updateValue(Int(each[1])! , forKey: each[0])
              })
              print(fillDefaultColorsDictionary)
      
              self.calendar.dataSource = self
              self.calendar.delegate = self
              self.calendar.register(FSCalendarCell.self, forCellReuseIdentifier: "CELL")
              self.calendar.allowsMultipleSelection = true
              self.calendar.swipeToChooseGesture.isEnabled = true
              self.calendar.appearance.caseOptions = [.headerUsesUpperCase,.weekdayUsesSingleUpperCase]
      
          }
      
      
          //날짜가 선택되어있을때
          func calendar(_ calendar: FSCalendar, didSelect date: Date, at monthPosition: FSCalendarMonthPosition) {
              let date_string = self.dateFormatter.string(from: date)
              //삭제
              if self.SegmentedControl.selectedSegmentIndex == 4 && fillDefaultColorsDictionary[date_string] != nil {
                  if (DB.delete(statement: Quary.Delete(Tablename: "Calendar", Condition: "marked_date = " + "'\(date_string)'"))){
                      print("delete success at calander")
                  }
              }else{
                  //기존 존재한다면 삭제하고 삽입한다.
                  if (DB.delete(statement: Quary.Delete(Tablename: "Calendar", Condition: "marked_date = " + "'\(date_string)'"))){
                      print("delete success at calander before insert")
                  }
                  if (DB.insert(statement: Quary.insert(Tablename: "Calendar", Values: " '\(date_string)', \(SegmentedControl.selectedSegmentIndex + 1)" ))){
                      print("insert success at calander")
                  }
              }
              fillDefaultColorsDictionary.updateValue(SegmentedControl.selectedSegmentIndex + 1 , forKey: date_string)
              //print(fillDefaultColorsDictionary)
              calendar.deselect(date)
              calendar.reloadData()
          }
      
          //기본색상
          func calendar(_ calendar: FSCalendar, appearance: FSCalendarAppearance, fillDefaultColorFor date: Date) -> UIColor? {
              print("언제실행되는가?")
              let key = self.dateFormatter.string(from: date)
              if let colorindex = fillDefaultColorsDictionary[key] {
                  return SegmentedBarColor[colorindex-1]
              }else{
                  return  appearance.borderSelectionColor
              }
          }
      
      }
      

      2.각각 셀에 원형의 색상이 아닌, 사각형의 색상을 입히고 싶은데, 어떻게 할 수 있을 까요?

      1. today를 배경색상이나, 글씨색상의 변화없이 테두리의 색상만 주고 싶은데 어떻게 할 수 있을까요?
      • 이 답변은 정재 이에 의해 4 years, 7 months 전에 수정됐습니다.
      • 이 답변은 정재 이에 의해 4 years, 7 months 전에 수정됐습니다.
      • 이 답변은 정재 이에 의해 4 years, 7 months 전에 수정됐습니다.
    • 김수호 김
      참가자
      • 글작성 : 0
      • 답글작성 : 5
      calendar.appearance.borderRadius = value
      

      바로 답변해드릴 수 있는거 먼저 해드릴게요 .

      셀이 사각형으로 변하는게 상관없으시다면 … 이거 쓰셔도 될거같습니다 . 

    • 야곰
      키 마스터
      • 글작성 : 37
      • 답글작성 : 579

      선택했을 때 동작할 if-else 구문의 코드에 논리적 오류가 포함되어 있는 것은 아닐까요? break point 찍어서 확인해보면 좋을것 같아요.
      디버깅 방법을 잘 모르면 LLDB 정복 코스를 참고해서 익혀보세요. 저 내용을 익히는 것이 시간이 많이 걸리는 것 같고 돌아가는 길 같지만, 간단한 디버깅 명령어 하나로 금방 찾을 수 있는 문제를 일주일 가까이 씨름하는 것보다는 훨씬 빨리가는 지름길입니다. 마음이 급할수록 돌아가보세요. LLDB 익히면 초보에서 중급으로 훌쩍 실력이 급상승 할겁니다.

      질문과는 논외로 저도 질문이 있는데요, 위에 들여쓰기가 안된 코드는 어떻게 했을 때 들여쓰기가 안됐고, 어떻게 하니 들여쓰기가 됐는지 궁금합니다. +_+

    • 정재 이
      참가자
      • 글작성 : 4
      • 답글작성 : 11

      들여쓰기는 제가 마크다운 형식으로 코드를 작성했는데, 글올리기를 하면 스크립트 타입으로 자동으로 바꿔주더라고요! 그걸 다시 수정하려고 할때 코드 스크립트 앞뒤에 추가적으로 스크립트가 감싸서 그랬던것같습니다!

      • 야곰
        키 마스터
        • 글작성 : 37
        • 답글작성 : 579

        그렇군요…! 두 번째로 작성한 댓글은 수정했어도 들여쓰기가 되어있는데 저도 헷갈리네요 +_+

        • 정재 이
          참가자
          • 글작성 : 4
          • 답글작성 : 11

          아니면 제가 사이트에서 코드를 복사해와서 그런 것 일수도 있어요! 다른 사이트에도 이러한 질문을 올렸는데 그 때 사용한 마크다운을 그대로 복사해서 사용해서 일수도… 나머지는 xcode에서 복붙했어요!

6 답변 글타래를 보이고 있습니다
  • 답변은 로그인 후 가능합니다.

logo landscape small

사업자번호 : 743-81-02195
통신판매업 신고번호 : 제 2022-충북청주-1278 호
고객센터 : 카카오톡채널 @yagom