A calendar based heatmap which presenting a time series of data points in colors.

Overview

Calendar Heatmap

CalendarHeatmap Title

CI Status Version License Platform

example

Introduction

CalendarHeatmap is a calendar based heatmap which presenting a time series of data points in colors, inspired by Github contribution chart, and written in Swift.

Installation

CalendarHeatmap is available through CocoaPods. To install it, simply add the following line to your Podfile:

pod 'CalendarHeatmap'

CalendarHeatmap is also availabele through Carthage, by adding it to your Cartfile:

github "Zacharysp/CalendarHeatmap"

And finally CalendarHeatmap can also be installed using the Swift Package Manager:

Usage

// minimum usage.
let startDate = Date()
let calendarHeatmap = CalendarHeatmap(startDate: startDate)
calendarHeatmap.delegate = self
view.addSubview(calendarHeatmap)
// provide a range of date.
let formatter = DateFormatter()
formatter.dateFormat = "yyyy-MM-dd"
let startDate = formatter.date(from: "2019-10-18")
let endDate = formatter.date(from: "2020-02-14")
// default endDate is now.
let calendarHeatmap = CalendarHeatmap(startDate: startDate, endDate: endDate)
// you could custom the heatmap by using CalendarHeatmapConfig.
let config = CalendarHeatmapConfig()
let calendarHeatmap = CalendarHeatmap(config: config, startDate: Date())
// reload the heatmap
let calendarHeatmap = CalendarHeatmap(startDate: ...)
calendarHeatmap.reload()
// reload with new range of date.
calendarHeatmap.reload(newStartDate: ..., newEndDate: ...)

CalendarHeatmapConfig details.

Config Key Type Default
backgroundColor UIColor UIColor.white
contentRightInset CGFloat 60
itemColor UIColor UIColor.clear
itemSide CGFloat 20
interitemSpacing CGFloat 4
lineSpacing CGFloat 4
weekDayColor UIColor UIColor.black
weekDayStrings [String] DateFormatter().shortWeekdaySymbols.map{ \$0.capitalized }
weekDayFont UIFont UIFont.systemFont(ofSize: 12, weight: .medium)
weekDayWidth CGFloat 30
weekDayStandard Enum USandCanada
monthColor UIColor UIColor.black
monthStrings [String] DateFormatter().monthSymbols
monthFont UIFont UIFont.systemFont(ofSize: 12, weight: .medium)
monthHeight CGFloat 20

Starts Monday or Sunday.

var config = CalendarHeatmapConfig()
config.weekDayStandard = .USandCanada // starts Sunday. (default)
config.weekDayStandard = .International // starts Monday

Scroll the calendar programmatically

calendarHeatMap.scrollTo(date: Date(...), at: .right, animated: false)

Make your ViewController adopts CalendarHeatmapDelegate

// color for date
func colorFor(dateComponents: DateComponents) -> UIColor {
    guard let year = dateComponents.year,
        let month = dateComponents.month,
        let day = dateComponents.day else { return .clear}
    // manage your color based on date here
    let yourColor = {...}
    return yourColor
}

// (optional) selection at date
func didSelectedAt(dateComponents: DateComponents) {
    guard let year = dateComponents.year,
    let month = dateComponents.month,
    let day = dateComponents.day else { return }
    // do something here
}

// (optional) notify finish loading the calendar
func finishLoadCalendar() {
    // do something here
}

Demo

Take a look at Example, to run the example project, clone the repo, and run pod install from the Example directory first.

Author

Zacharysp, [email protected]

License

CalendarHeatmap is available under the MIT license. See the LICENSE file for more info.

Comments
  • StartDate is being overridden

    StartDate is being overridden

    Hi Zachary

    me again.

    You are overriding the startDate, that I am lovingly calculating.

    HeatmapCalendar.swift > function private func setup(completion: @escaping () -> Void) { startDate: self.startDate.startOfMonth(),

    Is there an option of making this optional ;-)

    Kind Regards Graham

    enhancement 
    opened by glancashire 2
  • Weird scrolling

    Weird scrolling

    Hi Zachary

    Thank you for your quick turnaround, just tell me if I ask too much.

    There is a slight scrolling problem, which I cannot explain. See screenshots.

    On initial load the heat map scrolls such, that the first date is not visible. calendarheatmap_onload

    Even though there is enough space to display the first date when scrolling manually. calendarheatmap_scroll

    A simple solution would be to allow configuration if the heatmap should be scrolled to the beginning or end on load.

    Cheers, Graham

    enhancement 
    opened by glancashire 2
  • A reload function would be nice

    A reload function would be nice

    Thanks again for your control.

    For usage in cells the option of reloading w/o recreating would be a great addition.

    I have added one via an extension (see below), but it is of course not a clean and has to be added to your source file (private access).

    Kind Regard Graham

    extension CalendarHeatmap {
        public func reload() {
            DispatchQueue.global(qos: .userInteractive).async {
                DispatchQueue.main.async { [weak self] in
                    // then reload
                    self?.collectionView.reloadData()
                    self?.scrollToEnd()
                }
            }
        }
    }
    
    enhancement 
    opened by glancashire 2
  • Start of week should be configurable to Monday

    Start of week should be configurable to Monday

    Dear Zachary

    Thanks for this beautiful control.

    It would be great for using this in Europe, if there were a way to configure the start of the week to be Monday instead of Sunday.

    Kind Regards Graham

    enhancement 
    opened by glancashire 2
  • The reload() method is not working

    The reload() method is not working

    The reload() method doesn't retrieve the data from plist. I want the user to input data from one screen and when they visit the screen with the heat map, I want the heat map to reflect the input data. But, the the heat map only reflects the data when the app is loaded for the first time, view.addSubview(calendarHeatMap), but when I use the reload() method any time after, the map doesn't reflect any additional data.

    override func viewWillAppear(_ animated: Bool) {
        super.viewWillAppear(animated)
        calendarHeatMap.reload()
    }
    
    lazy var calendarHeatMap: CalendarHeatmap = {
        var config = CalendarHeatmapConfig()
        config.backgroundColor = UIColor(ciColor: .white)
        // config item
        config.selectedItemBorderColor = .white
        config.allowItemSelection = true
        // config month header
        config.monthHeight = 30
        config.monthStrings = DateFormatter().shortMonthSymbols
        config.monthFont = UIFont.systemFont(ofSize: 18)
        config.monthColor = UIColor(ciColor: .black)
        // config weekday label on left
        config.weekDayFont = UIFont.systemFont(ofSize: 12)
        config.weekDayWidth = 30
        config.weekDayColor = UIColor(ciColor: .black)
        
        var dateComponent = DateComponents()
        let yearsBefore = -1
        dateComponent.year = yearsBefore
        if let startDate = Calendar.current.date(byAdding: dateComponent, to: Date()) {
            let calendar = CalendarHeatmap(config: config, startDate: startDate, endDate: Date())
            calendar.delegate = self
            return calendar
        } else {
            let calendar = CalendarHeatmap(config: config, startDate: Date(2019, 1, 1), endDate: Date())
            calendar.delegate = self
            return calendar
        }
    }()
    
    private func readHeatmap() -> [String: Int]? {
        guard let url = try? FileManager.default.url(for: .documentDirectory, in: .userDomainMask, appropriateFor: nil, create: false).appendingPathComponent("Heatmap.plist") else { return nil }
    
        return NSDictionary(contentsOf: url) as? [String: Int]
    }
    

    Everything else is pretty much the same as the example in this repo.

    When the screen is first loaded, the order of execution is:

    1. lazy var calendarHeatMap: CalendarHeatmap
    2. viewWillAppear() which has the calendarHeapmap.reload() method
    3. func readHeatmap()
    4. lazy var data: [String: UIColor]
    5. func finishLoadCalendar()

    or

    1. lazy var calendarHeatMap: CalendarHeatmap
    2. func readHeatmap()
    3. lazy var data: [String: UIColor]
    4. func finishLoadCalendar()
    5. viewDidAppear() which has the calendarHeapmap.reload() method

    However, when the screen is revisited, none of these are called, except for the view's life cycle methods.

    opened by igibliss00 1
  • Support Saturday as first day of week

    Support Saturday as first day of week

    Thanks a lot for this beautiful library. I would like to request the following feature:

    Currently, Sunday and Morning are supported as the first day of the week (in the weekDayStandard enum). However, in many countries of the Middle East and North Africa, the first day of the week is Saturday. It would be great if you could support this.

    You can check the first day of the week by country in the Unicode Common Locale Data Repository (CLDR). According to that information, the following countries have Saturday as the first day of the week (alphabetical order): Afghanistan, Algeria, Bahrain, Djibouti, Egypt, Iran, Iraq, Jordan, Kuwait, Libya, Oman, Qatar, Sudan, Syria, United Arab Emirates.

    opened by noe 0
  • Date changed but the view not update automatically - using framework in SwiftUI

    Date changed but the view not update automatically - using framework in SwiftUI

    Hi, I'm a newbie developer and using SwiftUI for interface development.

    So I managed to embed your framework into the SwiftUI and using the custom data function for the heatmap data. WX20210530-205702

    Everything works great but when the heatmap data changed, the heatmap view doesn't update automatically - unless I close and reopen the page again. I've searched and tried everything I can, but none of those works. Could you please give me some advice on this, or there is already a solution for this but I'm using it in the wrong way?

    Thanks!

    opened by AngusYahn 1
Owner
null
RCalendarPicker A date picker control, Calendar calendar control, select control, calendar, date selection, the clock selection control.

RCalendarPicker RCalendarPicker Calendar calendar control, select control, calendar, date selection, the clock selection control. 日历控件 ,日历选择控件,日历,日期选择

杜耀辉 131 Jul 18, 2022
A declarative, performant, iOS calendar UI component that supports use cases ranging from simple date pickers all the way up to fully-featured calendar apps.

HorizonCalendar A declarative, performant, calendar UI component that supports use cases ranging from simple date pickers all the way up to fully-feat

Airbnb 2.2k Jan 4, 2023
Simple customizable calendar component in Swift :calendar:

Koyomi Koyomi is a simple calendar view framework for iOS, written in Swift ?? Content Features Demo App Usage introduction : Change displayed month,

Shohei Yokoyama 741 Dec 24, 2022
Malendar is a personal calendar app that connects to your default calendar and lets you add/delete events

Malendar is a personal calendar app that connects to your default calendar and lets you add/delete events. It will gather events from your default iOS calendar.

Chase 194 Jan 4, 2023
NextEvent is a countdown widget for your Mac menu bar. It displays the time until the next event in your calendar or task list.

NextEvent NextEvent is a countdown widget for your Mac menu bar. It displays the time until the next event in your calendar or reminders. Choose the n

Paul Wong 3 Nov 26, 2022
An iOS pre-permissions utility that lets developers ask users on their own dialog for calendar, contacts, location, photos, reminders, twitter, push notifications and more, before making the system-based permission request.

An iOS pre-permissions utility that lets developers ask users on their own dialog for calendar, contacts, location, photos, reminders, twitter, push notifications and more, before making the system-based permission request.

Joe L 420 Dec 22, 2022
📅 Calendar for iOS, iPadOS and macOS in Swift

CalendarKit CalendarKit is a Swift calendar UI library for iOS, iPadOS and Mac Catalyst. It looks similar to the Apple Calendar app out-of-the-box, wh

Richard Topchii 2.2k Jan 5, 2023
An Easy to Use Calendar for iOS (Swift 5.0)

This is an easy to use, "just drag and drop it in your code" type of calendar for iOS. It supports both vertical and horizontal scrolling, as well as

Michael Michailidis 525 Dec 23, 2022
The elegant full screen calendar missed in SwiftUI.

ElegantCalendar ElegantCalendar is an efficient and customizable full screen calendar written in SwiftUI. ElegantTimeline - Shows what's possible usin

Kevin Li 553 Dec 27, 2022
SwiftUI Simple Calendar / Date Picker for iOS

RKCalendar RKCalendar is a SwiftUI Calendar / Date Picker for iOS. Features include: minimum and maximum calendar dates selectable, single date select

null 453 Dec 28, 2022
A customizable swiftui calendar

Description not available. Installation From Xcode 11, you can use Swift Package Manager to add Kingfisher to your project. Select File > Swift Packag

Heshan Yodagama 140 Dec 24, 2022
An easy to use SwiftUI date picker for Shamsi (Persian) calendar

ShamsiDatePicker An easy-to-use SwiftUI iOS/watchOS date picker for Shamsi (Persian) calendar. Features Pure (100%) SwiftUI implementation Full suppor

Seyyed Parsa Neshaei 20 Nov 24, 2022
SwiftUICalendar - SwiftUI simple calendar

SwiftUICalendar Installation CocoaPods pod 'SwiftUICalendar' import import SwiftUICalendar Features Infinite scroll Support horizontal and vertical sc

null 59 Dec 27, 2022
Dead simple calendar implementation

Package provides a CalendarView which can be used to display simple calendar in your App.

Sergei Kononov 4 Oct 7, 2022
A calendar quick view for the MacOS status bar

Calendar Quick View Quick Menu Calendar in the mac app store An open source macOS calendar preview utility Download from the Mac App Store Visualizati

Michaellis 18 Oct 26, 2022
Clendar - universal calendar app. Written in SwiftUI. Available on App Store. MIT License.

Clendar - minimal calendar Minimal Calendar & Widgets Landing Page About This project is started out as an UIKit base app for me to learn new WWDC fea

Vinh Nguyen 418 Dec 30, 2022
A custom visual calendar for iOS 8+ written in Swift (>= 4.0).

Overview Screenshots GIF Demo Installation Usage Architecture Version matrix Advanced API For contributors Screenshots GIF Demo Installation CocoaPods

null 3.5k Dec 24, 2022
iOS 7+ Calendar (Date Picker) with Infinite Scrolling.

RSDayFlow iOS 7 Calendar with Infinite Scrolling. Only need 4 lines of code to set up. RSDayFlow is a slim fork of DayFlow with updates and extensions

Ruslan Skorb 844 Sep 14, 2022
An availability calendar implementation for iOS

NWCalendarView NWCalendar View is an iOS control that displays a calendar. It is perfect for appointment or availibilty selection. It allows for selec

Nicholas Wargnier 60 May 27, 2021