├── AVCalendarFramework ├── AVCalendarFramework.framework │ ├── AVCalendarFramework │ ├── Assets.car │ ├── Calendar.storyboardc │ │ ├── 66b-cS-S1A-view-bSx-22-IJQ.nib │ │ ├── AVCalendarViewController.nib │ │ ├── Info.plist │ │ ├── TEV-Hz-sya-view-xz4-2y-vjh.nib │ │ ├── UINavigationController-TaW-6V-vyl.nib │ │ └── UIViewController-TEV-Hz-sya.nib │ ├── Headers │ │ ├── AVCalendarFramework-Swift.h │ │ └── AVCalendarFramework.h │ ├── Info.plist │ ├── Modules │ │ ├── AVCalendarFramework.swiftmodule │ │ │ ├── arm64.swiftdoc │ │ │ ├── arm64.swiftmodule │ │ │ ├── x86_64.swiftdoc │ │ │ └── x86_64.swiftmodule │ │ └── module.modulemap │ └── ios-framework-build.sh ├── AVCalendarFramework.podspec ├── LICENSE └── README.md ├── AVCalendarSample ├── AVCalendar │ ├── CustomCalendarController │ │ ├── APCalendarViewController.swift │ │ ├── APCustomCalendarContainer.swift │ │ ├── APCustomCalenderCells │ │ │ └── APCustomCalendarYearCell.swift │ │ ├── APHorizontalScrollCollectionView.swift │ │ ├── Calendar.storyboard │ │ └── CalendarAssets.xcassets │ │ │ ├── Contents.json │ │ │ ├── calendar_check.imageset │ │ │ ├── Contents.json │ │ │ ├── calendar_check.png │ │ │ ├── calendar_check@2x.png │ │ │ └── calendar_check@3x.png │ │ │ ├── calendar_left_month_gradient.imageset │ │ │ ├── Contents.json │ │ │ ├── calendar_left_month_gradient.png │ │ │ ├── calendar_left_month_gradient@2x.png │ │ │ └── calendar_left_month_gradient@3x.png │ │ │ ├── calendar_left_year_gradient.imageset │ │ │ ├── Contents.json │ │ │ ├── calendar_left_year_gradient.png │ │ │ ├── calendar_left_year_gradient@2x.png │ │ │ └── calendar_left_year_gradient@3x.png │ │ │ ├── calendar_partition.imageset │ │ │ ├── Contents.json │ │ │ ├── calendar_partition.png │ │ │ ├── calendar_partition@2x.png │ │ │ └── calendar_partition@3x.png │ │ │ ├── calendar_right_month_gradient.imageset │ │ │ ├── Contents.json │ │ │ ├── calendar_right_month_gradient.png │ │ │ ├── calendar_right_month_gradient@2x.png │ │ │ └── calendar_right_month_gradient@3x.png │ │ │ └── calendar_right_year_gradient.imageset │ │ │ ├── Contents.json │ │ │ ├── calendar_right_year_gradient.png │ │ │ ├── calendar_right_year_gradient@2x.png │ │ │ └── calendar_right_year_gradient@3x.png │ ├── DynamicType │ │ └── APDynamicType.swift │ └── Protocols │ │ └── HapticFeedbackGenerator.swift ├── AVCalendarSample.xcodeproj │ ├── project.pbxproj │ ├── project.xcworkspace │ │ ├── xcshareddata │ │ │ └── IDEWorkspaceChecks.plist │ │ └── xcuserdata │ │ │ └── anirudh-personal.xcuserdatad │ │ │ └── UserInterfaceState.xcuserstate │ └── xcuserdata │ │ └── anirudh-personal.xcuserdatad │ │ └── xcschemes │ │ └── xcschememanagement.plist ├── AVCalendarSample │ ├── AppDelegate.swift │ ├── Assets.xcassets │ │ ├── AppIcon.appiconset │ │ │ └── Contents.json │ │ └── Contents.json │ ├── Base.lproj │ │ ├── LaunchScreen.storyboard │ │ └── Main.storyboard │ ├── Info.plist │ ├── Screenshot.png │ └── ViewController.swift ├── AVCalendarSampleTests │ ├── AVCalendarSampleTests.swift │ └── Info.plist └── AVCalendarSampleUITests │ ├── AVCalendarSampleUITests.swift │ └── Info.plist ├── LICENSE └── README.md /AVCalendarFramework/AVCalendarFramework.framework/AVCalendarFramework: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarFramework/AVCalendarFramework.framework/AVCalendarFramework -------------------------------------------------------------------------------- /AVCalendarFramework/AVCalendarFramework.framework/Assets.car: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarFramework/AVCalendarFramework.framework/Assets.car -------------------------------------------------------------------------------- /AVCalendarFramework/AVCalendarFramework.framework/Calendar.storyboardc/66b-cS-S1A-view-bSx-22-IJQ.nib: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarFramework/AVCalendarFramework.framework/Calendar.storyboardc/66b-cS-S1A-view-bSx-22-IJQ.nib -------------------------------------------------------------------------------- /AVCalendarFramework/AVCalendarFramework.framework/Calendar.storyboardc/AVCalendarViewController.nib: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarFramework/AVCalendarFramework.framework/Calendar.storyboardc/AVCalendarViewController.nib -------------------------------------------------------------------------------- /AVCalendarFramework/AVCalendarFramework.framework/Calendar.storyboardc/Info.plist: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarFramework/AVCalendarFramework.framework/Calendar.storyboardc/Info.plist -------------------------------------------------------------------------------- /AVCalendarFramework/AVCalendarFramework.framework/Calendar.storyboardc/TEV-Hz-sya-view-xz4-2y-vjh.nib: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarFramework/AVCalendarFramework.framework/Calendar.storyboardc/TEV-Hz-sya-view-xz4-2y-vjh.nib -------------------------------------------------------------------------------- /AVCalendarFramework/AVCalendarFramework.framework/Calendar.storyboardc/UINavigationController-TaW-6V-vyl.nib: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarFramework/AVCalendarFramework.framework/Calendar.storyboardc/UINavigationController-TaW-6V-vyl.nib -------------------------------------------------------------------------------- /AVCalendarFramework/AVCalendarFramework.framework/Calendar.storyboardc/UIViewController-TEV-Hz-sya.nib: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarFramework/AVCalendarFramework.framework/Calendar.storyboardc/UIViewController-TEV-Hz-sya.nib -------------------------------------------------------------------------------- /AVCalendarFramework/AVCalendarFramework.framework/Headers/AVCalendarFramework-Swift.h: -------------------------------------------------------------------------------- 1 | // Generated by Apple Swift version 5.0.1 (swiftlang-1001.0.82.4 clang-1001.0.46.5) 2 | #pragma clang diagnostic push 3 | #pragma clang diagnostic ignored "-Wgcc-compat" 4 | 5 | #if !defined(__has_include) 6 | # define __has_include(x) 0 7 | #endif 8 | #if !defined(__has_attribute) 9 | # define __has_attribute(x) 0 10 | #endif 11 | #if !defined(__has_feature) 12 | # define __has_feature(x) 0 13 | #endif 14 | #if !defined(__has_warning) 15 | # define __has_warning(x) 0 16 | #endif 17 | 18 | #if __has_include() 19 | # include 20 | #endif 21 | 22 | #pragma clang diagnostic ignored "-Wauto-import" 23 | #include 24 | #include 25 | #include 26 | #include 27 | 28 | #if !defined(SWIFT_TYPEDEFS) 29 | # define SWIFT_TYPEDEFS 1 30 | # if __has_include() 31 | # include 32 | # elif !defined(__cplusplus) 33 | typedef uint_least16_t char16_t; 34 | typedef uint_least32_t char32_t; 35 | # endif 36 | typedef float swift_float2 __attribute__((__ext_vector_type__(2))); 37 | typedef float swift_float3 __attribute__((__ext_vector_type__(3))); 38 | typedef float swift_float4 __attribute__((__ext_vector_type__(4))); 39 | typedef double swift_double2 __attribute__((__ext_vector_type__(2))); 40 | typedef double swift_double3 __attribute__((__ext_vector_type__(3))); 41 | typedef double swift_double4 __attribute__((__ext_vector_type__(4))); 42 | typedef int swift_int2 __attribute__((__ext_vector_type__(2))); 43 | typedef int swift_int3 __attribute__((__ext_vector_type__(3))); 44 | typedef int swift_int4 __attribute__((__ext_vector_type__(4))); 45 | typedef unsigned int swift_uint2 __attribute__((__ext_vector_type__(2))); 46 | typedef unsigned int swift_uint3 __attribute__((__ext_vector_type__(3))); 47 | typedef unsigned int swift_uint4 __attribute__((__ext_vector_type__(4))); 48 | #endif 49 | 50 | #if !defined(SWIFT_PASTE) 51 | # define SWIFT_PASTE_HELPER(x, y) x##y 52 | # define SWIFT_PASTE(x, y) SWIFT_PASTE_HELPER(x, y) 53 | #endif 54 | #if !defined(SWIFT_METATYPE) 55 | # define SWIFT_METATYPE(X) Class 56 | #endif 57 | #if !defined(SWIFT_CLASS_PROPERTY) 58 | # if __has_feature(objc_class_property) 59 | # define SWIFT_CLASS_PROPERTY(...) __VA_ARGS__ 60 | # else 61 | # define SWIFT_CLASS_PROPERTY(...) 62 | # endif 63 | #endif 64 | 65 | #if __has_attribute(objc_runtime_name) 66 | # define SWIFT_RUNTIME_NAME(X) __attribute__((objc_runtime_name(X))) 67 | #else 68 | # define SWIFT_RUNTIME_NAME(X) 69 | #endif 70 | #if __has_attribute(swift_name) 71 | # define SWIFT_COMPILE_NAME(X) __attribute__((swift_name(X))) 72 | #else 73 | # define SWIFT_COMPILE_NAME(X) 74 | #endif 75 | #if __has_attribute(objc_method_family) 76 | # define SWIFT_METHOD_FAMILY(X) __attribute__((objc_method_family(X))) 77 | #else 78 | # define SWIFT_METHOD_FAMILY(X) 79 | #endif 80 | #if __has_attribute(noescape) 81 | # define SWIFT_NOESCAPE __attribute__((noescape)) 82 | #else 83 | # define SWIFT_NOESCAPE 84 | #endif 85 | #if __has_attribute(warn_unused_result) 86 | # define SWIFT_WARN_UNUSED_RESULT __attribute__((warn_unused_result)) 87 | #else 88 | # define SWIFT_WARN_UNUSED_RESULT 89 | #endif 90 | #if __has_attribute(noreturn) 91 | # define SWIFT_NORETURN __attribute__((noreturn)) 92 | #else 93 | # define SWIFT_NORETURN 94 | #endif 95 | #if !defined(SWIFT_CLASS_EXTRA) 96 | # define SWIFT_CLASS_EXTRA 97 | #endif 98 | #if !defined(SWIFT_PROTOCOL_EXTRA) 99 | # define SWIFT_PROTOCOL_EXTRA 100 | #endif 101 | #if !defined(SWIFT_ENUM_EXTRA) 102 | # define SWIFT_ENUM_EXTRA 103 | #endif 104 | #if !defined(SWIFT_CLASS) 105 | # if __has_attribute(objc_subclassing_restricted) 106 | # define SWIFT_CLASS(SWIFT_NAME) SWIFT_RUNTIME_NAME(SWIFT_NAME) __attribute__((objc_subclassing_restricted)) SWIFT_CLASS_EXTRA 107 | # define SWIFT_CLASS_NAMED(SWIFT_NAME) __attribute__((objc_subclassing_restricted)) SWIFT_COMPILE_NAME(SWIFT_NAME) SWIFT_CLASS_EXTRA 108 | # else 109 | # define SWIFT_CLASS(SWIFT_NAME) SWIFT_RUNTIME_NAME(SWIFT_NAME) SWIFT_CLASS_EXTRA 110 | # define SWIFT_CLASS_NAMED(SWIFT_NAME) SWIFT_COMPILE_NAME(SWIFT_NAME) SWIFT_CLASS_EXTRA 111 | # endif 112 | #endif 113 | 114 | #if !defined(SWIFT_PROTOCOL) 115 | # define SWIFT_PROTOCOL(SWIFT_NAME) SWIFT_RUNTIME_NAME(SWIFT_NAME) SWIFT_PROTOCOL_EXTRA 116 | # define SWIFT_PROTOCOL_NAMED(SWIFT_NAME) SWIFT_COMPILE_NAME(SWIFT_NAME) SWIFT_PROTOCOL_EXTRA 117 | #endif 118 | 119 | #if !defined(SWIFT_EXTENSION) 120 | # define SWIFT_EXTENSION(M) SWIFT_PASTE(M##_Swift_, __LINE__) 121 | #endif 122 | 123 | #if !defined(OBJC_DESIGNATED_INITIALIZER) 124 | # if __has_attribute(objc_designated_initializer) 125 | # define OBJC_DESIGNATED_INITIALIZER __attribute__((objc_designated_initializer)) 126 | # else 127 | # define OBJC_DESIGNATED_INITIALIZER 128 | # endif 129 | #endif 130 | #if !defined(SWIFT_ENUM_ATTR) 131 | # if defined(__has_attribute) && __has_attribute(enum_extensibility) 132 | # define SWIFT_ENUM_ATTR(_extensibility) __attribute__((enum_extensibility(_extensibility))) 133 | # else 134 | # define SWIFT_ENUM_ATTR(_extensibility) 135 | # endif 136 | #endif 137 | #if !defined(SWIFT_ENUM) 138 | # define SWIFT_ENUM(_type, _name, _extensibility) enum _name : _type _name; enum SWIFT_ENUM_ATTR(_extensibility) SWIFT_ENUM_EXTRA _name : _type 139 | # if __has_feature(generalized_swift_name) 140 | # define SWIFT_ENUM_NAMED(_type, _name, SWIFT_NAME, _extensibility) enum _name : _type _name SWIFT_COMPILE_NAME(SWIFT_NAME); enum SWIFT_COMPILE_NAME(SWIFT_NAME) SWIFT_ENUM_ATTR(_extensibility) SWIFT_ENUM_EXTRA _name : _type 141 | # else 142 | # define SWIFT_ENUM_NAMED(_type, _name, SWIFT_NAME, _extensibility) SWIFT_ENUM(_type, _name, _extensibility) 143 | # endif 144 | #endif 145 | #if !defined(SWIFT_UNAVAILABLE) 146 | # define SWIFT_UNAVAILABLE __attribute__((unavailable)) 147 | #endif 148 | #if !defined(SWIFT_UNAVAILABLE_MSG) 149 | # define SWIFT_UNAVAILABLE_MSG(msg) __attribute__((unavailable(msg))) 150 | #endif 151 | #if !defined(SWIFT_AVAILABILITY) 152 | # define SWIFT_AVAILABILITY(plat, ...) __attribute__((availability(plat, __VA_ARGS__))) 153 | #endif 154 | #if !defined(SWIFT_DEPRECATED) 155 | # define SWIFT_DEPRECATED __attribute__((deprecated)) 156 | #endif 157 | #if !defined(SWIFT_DEPRECATED_MSG) 158 | # define SWIFT_DEPRECATED_MSG(...) __attribute__((deprecated(__VA_ARGS__))) 159 | #endif 160 | #if __has_feature(attribute_diagnose_if_objc) 161 | # define SWIFT_DEPRECATED_OBJC(Msg) __attribute__((diagnose_if(1, Msg, "warning"))) 162 | #else 163 | # define SWIFT_DEPRECATED_OBJC(Msg) SWIFT_DEPRECATED_MSG(Msg) 164 | #endif 165 | #if __has_feature(modules) 166 | #if __has_warning("-Watimport-in-framework-header") 167 | #pragma clang diagnostic ignored "-Watimport-in-framework-header" 168 | #endif 169 | @import ObjectiveC; 170 | @import UIKit; 171 | #endif 172 | 173 | #pragma clang diagnostic ignored "-Wproperty-attribute-mismatch" 174 | #pragma clang diagnostic ignored "-Wduplicate-method-arg" 175 | #if __has_warning("-Wpragma-clang-attribute") 176 | # pragma clang diagnostic ignored "-Wpragma-clang-attribute" 177 | #endif 178 | #pragma clang diagnostic ignored "-Wunknown-pragmas" 179 | #pragma clang diagnostic ignored "-Wnullability" 180 | 181 | #if __has_attribute(external_source_symbol) 182 | # pragma push_macro("any") 183 | # undef any 184 | # pragma clang attribute push(__attribute__((external_source_symbol(language="Swift", defined_in="AVCalendarFramework",generated_declaration))), apply_to=any(function,enum,objc_interface,objc_category,objc_protocol)) 185 | # pragma pop_macro("any") 186 | #endif 187 | 188 | 189 | SWIFT_CLASS("_TtC19AVCalendarFramework19AVCalendarFramework") 190 | @interface AVCalendarFramework : NSObject 191 | - (nonnull instancetype)init OBJC_DESIGNATED_INITIALIZER; 192 | @end 193 | 194 | @class UIStoryboardSegue; 195 | @class NSBundle; 196 | @class NSCoder; 197 | 198 | SWIFT_CLASS("_TtC19AVCalendarFramework24AVCalendarViewController") 199 | @interface AVCalendarViewController : UIViewController 200 | - (void)viewWillAppear:(BOOL)animated; 201 | - (void)viewDidLoad; 202 | - (void)prepareForSegue:(UIStoryboardSegue * _Nonnull)segue sender:(id _Nullable)sender; 203 | - (nonnull instancetype)initWithNibName:(NSString * _Nullable)nibNameOrNil bundle:(NSBundle * _Nullable)nibBundleOrNil OBJC_DESIGNATED_INITIALIZER; 204 | - (nullable instancetype)initWithCoder:(NSCoder * _Nonnull)aDecoder OBJC_DESIGNATED_INITIALIZER; 205 | @end 206 | 207 | #if __has_attribute(external_source_symbol) 208 | # pragma clang attribute pop 209 | #endif 210 | #pragma clang diagnostic pop 211 | -------------------------------------------------------------------------------- /AVCalendarFramework/AVCalendarFramework.framework/Headers/AVCalendarFramework.h: -------------------------------------------------------------------------------- 1 | // 2 | // AVCalendarFramework.h 3 | // AVCalendarFramework 4 | // 5 | // Created by Anirudh on 01/05/19. 6 | // Copyright © 2019 Anirudh Vyas. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | //! Project version number for AVCalendarFramework. 12 | FOUNDATION_EXPORT double AVCalendarFrameworkVersionNumber; 13 | 14 | //! Project version string for AVCalendarFramework. 15 | FOUNDATION_EXPORT const unsigned char AVCalendarFrameworkVersionString[]; 16 | 17 | // In this header, you should import all the public headers of your framework using statements like #import 18 | 19 | 20 | -------------------------------------------------------------------------------- /AVCalendarFramework/AVCalendarFramework.framework/Info.plist: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarFramework/AVCalendarFramework.framework/Info.plist -------------------------------------------------------------------------------- /AVCalendarFramework/AVCalendarFramework.framework/Modules/AVCalendarFramework.swiftmodule/arm64.swiftdoc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarFramework/AVCalendarFramework.framework/Modules/AVCalendarFramework.swiftmodule/arm64.swiftdoc -------------------------------------------------------------------------------- /AVCalendarFramework/AVCalendarFramework.framework/Modules/AVCalendarFramework.swiftmodule/arm64.swiftmodule: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarFramework/AVCalendarFramework.framework/Modules/AVCalendarFramework.swiftmodule/arm64.swiftmodule -------------------------------------------------------------------------------- /AVCalendarFramework/AVCalendarFramework.framework/Modules/AVCalendarFramework.swiftmodule/x86_64.swiftdoc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarFramework/AVCalendarFramework.framework/Modules/AVCalendarFramework.swiftmodule/x86_64.swiftdoc -------------------------------------------------------------------------------- /AVCalendarFramework/AVCalendarFramework.framework/Modules/AVCalendarFramework.swiftmodule/x86_64.swiftmodule: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarFramework/AVCalendarFramework.framework/Modules/AVCalendarFramework.swiftmodule/x86_64.swiftmodule -------------------------------------------------------------------------------- /AVCalendarFramework/AVCalendarFramework.framework/Modules/module.modulemap: -------------------------------------------------------------------------------- 1 | framework module AVCalendarFramework { 2 | umbrella header "AVCalendarFramework.h" 3 | 4 | export * 5 | module * { export * } 6 | } 7 | 8 | module AVCalendarFramework.Swift { 9 | header "AVCalendarFramework-Swift.h" 10 | requires objc 11 | } 12 | -------------------------------------------------------------------------------- /AVCalendarFramework/AVCalendarFramework.framework/ios-framework-build.sh: -------------------------------------------------------------------------------- 1 | APP_PATH="${TARGET_BUILD_DIR}/${WRAPPER_NAME}" 2 | 3 | # This script loops through the frameworks embedded in the application and 4 | 5 | # removes unused architectures. 6 | find "$APP_PATH" -name '*.framework' -type d | while read -r FRAMEWORK 7 | do 8 | FRAMEWORK_EXECUTABLE_NAME=$(defaults read "$FRAMEWORK/Info.plist" CFBundleExecutable) 9 | FRAMEWORK_EXECUTABLE_PATH="$FRAMEWORK/$FRAMEWORK_EXECUTABLE_NAME" 10 | echo "Executable is $FRAMEWORK_EXECUTABLE_PATH" 11 | 12 | EXTRACTED_ARCHS=() 13 | 14 | for ARCH in $ARCHS 15 | do 16 | echo "Extracting $ARCH from $FRAMEWORK_EXECUTABLE_NAME" 17 | lipo -extract "$ARCH" "$FRAMEWORK_EXECUTABLE_PATH" -o "$FRAMEWORK_EXECUTABLE_PATH-$ARCH" 18 | EXTRACTED_ARCHS+=("$FRAMEWORK_EXECUTABLE_PATH-$ARCH") 19 | done 20 | 21 | echo "Merging extracted architectures: ${ARCHS}" 22 | lipo -o "$FRAMEWORK_EXECUTABLE_PATH-merged" -create "${EXTRACTED_ARCHS[@]}" 23 | rm "${EXTRACTED_ARCHS[@]}" 24 | 25 | echo "Replacing original executable with thinned version" 26 | rm "$FRAMEWORK_EXECUTABLE_PATH" 27 | mv "$FRAMEWORK_EXECUTABLE_PATH-merged" "$FRAMEWORK_EXECUTABLE_PATH" 28 | 29 | done 30 | -------------------------------------------------------------------------------- /AVCalendarFramework/AVCalendarFramework.podspec: -------------------------------------------------------------------------------- 1 | Pod::Spec.new do |s| 2 | s.name = "AVCalendarFramework" 3 | s.version = "0.1.1" 4 | s.summary = "A brief description of AVCalendarFramework project." 5 | s.description = <<-DESC 6 | A customisable calendar framework. Which can be used to add a clear and a unique calendar to your application. 7 | DESC 8 | s.homepage = "http://dextraltech.com" 9 | s.license = { :type => 'Copyright', :text => <<-LICENSE 10 | Copyright 2018 11 | Permission is granted to... 12 | LICENSE 13 | } 14 | s.author = { "Anirudh Vyas" => "vyas.anirudh@hotmail.com" } 15 | s.source = { :git => "https://github.com/vyasanirudh/AVCalendarFramework.git", :tag => "#{s.version}" } 16 | s.public_header_files = "AVCalendarFramework.framework/Headers/*.h" 17 | s.source_files = "AVCalendarFramework.framework/Headers/*.h" 18 | s.vendored_frameworks = "AVCalendarFramework.framework" 19 | s.platform = :ios 20 | s.swift_version = "4.2" 21 | s.ios.deployment_target = '9.0' 22 | end 23 | -------------------------------------------------------------------------------- /AVCalendarFramework/LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2019 vyasanirudh 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /AVCalendarFramework/README.md: -------------------------------------------------------------------------------- 1 | # AVCalendarFramework 2 | A customisable iOS calendar view. 3 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/APCalendarViewController.swift: -------------------------------------------------------------------------------- 1 | // 2 | // AVCalendarViewController.swift 3 | // Anirudh Vyas 4 | // 5 | // Created by Anirudh on 08/05/19. 6 | // Copyright © 2019 Anirudh Vyas. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | private let reuseIdentifier = "Cell" 12 | 13 | open class AVCalendarViewController: UIViewController { 14 | 15 | @IBOutlet weak var closeButton: UIButton! { 16 | didSet { 17 | self.closeButton.transform = CGAffineTransform(scaleX: 0.01, y: 0.01) 18 | } 19 | } 20 | 21 | @IBOutlet weak var backgroundView: UIView! { 22 | didSet { 23 | 24 | } 25 | } 26 | 27 | @IBOutlet weak var containerView: UIView! { 28 | didSet { 29 | self.containerView.transform = CGAffineTransform(scaleX: 0.01, y: 0.01) 30 | } 31 | } 32 | 33 | public static var calendar: AVCalendarViewController = { 34 | let storyboard = UIStoryboard(name: "Calendar", bundle: Bundle(for: AVCalendarViewController.self)) 35 | let subscriptionPlansVC = storyboard.instantiateViewController(withIdentifier: "AVCalendarViewController") as! AVCalendarViewController 36 | subscriptionPlansVC.modalPresentationStyle = .overCurrentContext 37 | return subscriptionPlansVC 38 | }() 39 | 40 | private var _yearStyleComponents: CalendarComponentStyle? 41 | public var yearStyleComponents: CalendarComponentStyle? { 42 | get { 43 | return _yearStyleComponents 44 | } set { 45 | _yearStyleComponents = newValue 46 | calendarVC?.yearStyleComponents = newValue 47 | } 48 | } 49 | 50 | private var _monthStyleComponents: CalendarComponentStyle? 51 | public var monthStyleComponents: CalendarComponentStyle? { 52 | get { 53 | return _monthStyleComponents 54 | } set { 55 | _monthStyleComponents = newValue 56 | calendarVC?.monthStyleComponents = newValue 57 | } 58 | } 59 | 60 | private var _dateStyleComponents: CalendarComponentStyle? 61 | public var dateStyleComponents: CalendarComponentStyle? { 62 | get { 63 | return _dateStyleComponents 64 | } set { 65 | _dateStyleComponents = newValue 66 | calendarVC?.dateStyleComponents = newValue 67 | } 68 | } 69 | 70 | public var subscriber: ((AVDate?)->())? 71 | public var preSelectedDate: AVDate? { 72 | didSet { 73 | calendarVC?.preSelectedDate = preSelectedDate 74 | } 75 | } 76 | 77 | open override func viewWillAppear(_ animated: Bool) { 78 | super.viewWillAppear(animated) 79 | showCalendar() 80 | } 81 | 82 | private func showCalendar() { 83 | UIView.animate(withDuration: 0.6, delay: 0, usingSpringWithDamping: 0.45, initialSpringVelocity: 0, options: .curveEaseOut, animations: { 84 | self.containerView.alpha = 1.0 85 | self.closeButton.alpha = 1.0 86 | self.backgroundView.alpha = 1.0 87 | self.backgroundView.transform = .identity 88 | self.containerView.transform = .identity 89 | }) { (done) in 90 | UIView.animate(withDuration: 0.5, delay: 0, usingSpringWithDamping: 0.45, initialSpringVelocity: 0, options: .curveEaseOut, animations: { 91 | self.closeButton.transform = .identity 92 | }) { (done) in 93 | 94 | } 95 | } 96 | } 97 | 98 | private func hideCalendar() { 99 | 100 | } 101 | 102 | open override func viewDidLoad() { 103 | super.viewDidLoad() 104 | 105 | } 106 | 107 | private var calendarVC: AVCustomCalendarController? { 108 | didSet { 109 | calendarVC?.dateStyleComponents = _dateStyleComponents 110 | calendarVC?.monthStyleComponents = _monthStyleComponents 111 | calendarVC?.yearStyleComponents = _yearStyleComponents 112 | } 113 | } 114 | 115 | open override func prepare(for segue: UIStoryboardSegue, sender: Any?) { 116 | super.prepare(for: segue, sender: sender) 117 | if let vc = segue.destination as? AVCustomCalendarController { 118 | calendarVC = vc 119 | } 120 | } 121 | 122 | @IBAction func closeButtonAction(sender: UIButton) { 123 | if let vc = self.calendarVC { 124 | if let dateSelected = vc.getDate() { 125 | if dateSelected.day == nil { 126 | if let _subscriber = self.subscriber { 127 | _subscriber(nil) 128 | } 129 | return 130 | } else { 131 | if let _subscriber = self.subscriber { 132 | _subscriber(dateSelected) 133 | } 134 | } 135 | UIView.animate(withDuration: 0.3, delay: 0, usingSpringWithDamping: 1.0, initialSpringVelocity: 0, options: .curveEaseOut, animations: { 136 | self.containerView.alpha = 0.0 137 | self.closeButton.alpha = 0.0 138 | self.backgroundView.alpha = 0.0 139 | self.containerView.transform = CGAffineTransform(scaleX: 0.01, y: 0.01) 140 | self.closeButton.transform = CGAffineTransform(scaleX: 0.01, y: 0.01) 141 | }) { (done) in 142 | self.dismiss(animated: false, completion: nil) 143 | } 144 | } else { 145 | sender.generateFeedback() 146 | } 147 | } 148 | } 149 | 150 | deinit { 151 | print("") 152 | } 153 | } 154 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/APCustomCalendarContainer.swift: -------------------------------------------------------------------------------- 1 | // 2 | // AVCustomCalendarController.swift 3 | // Anirudh Vyas 4 | // 5 | // Created by Anirudh on 06/05/19. 6 | // Copyright © 2019 Anirudh Vyas. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | let AGE_LIMIT = 0 12 | 13 | public struct CalendarComponentStyle { 14 | var backgroundColor: UIColor? 15 | var textColor: UIColor? 16 | var highlightColor: UIColor? 17 | 18 | public init(backgroundColor: UIColor?, textColor: UIColor?, highlightColor:UIColor?) { 19 | self.backgroundColor = backgroundColor 20 | self.textColor = textColor 21 | self.highlightColor = highlightColor 22 | } 23 | 24 | } 25 | 26 | struct CalendarComponents { 27 | let years = (((Calendar.current.component(.year, from: Date()) - AGE_LIMIT)-100)...2099).map { String($0) } 28 | let months = ["Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sept","Oct","Nov","Dec"] 29 | let days = ["Mon","Tue","Wed","Thu","Fri","Sat","Sun"] 30 | var dates:Dynamic<[String]>! = Dynamic<[String]>((1...31).map { String($0) }) 31 | var masterDates:Dynamic<[String]>! = Dynamic<[String]>((1...31).map { String($0) }) 32 | } 33 | 34 | public struct AVDate { 35 | public var day: String? 36 | public var month: String? 37 | public var year: String? 38 | public var doubleVal: Double? 39 | } 40 | 41 | internal struct _AVDate { 42 | public var day: String? 43 | public var month: String? 44 | public var year: String? 45 | public var doubleVal: Double? { 46 | mutating get { 47 | let dfmatter = DateFormatter() 48 | dfmatter.dateFormat="yyyy-MM-dd'T'HH:mm:ssZ" 49 | dfmatter.timeZone = .current 50 | if let _year = year, let _month = calendarComponents.months.firstIndex(of: month!), let day = day, let _day = calendarComponents.dates.value?.firstIndex(of: day) { 51 | let _date = dfmatter.date(from: "\(_year)-\(_month + 1)-\(_day + 1)T00:00:00+0000") 52 | if let dateStamp = _date?.timeIntervalSince1970 { 53 | return dateStamp 54 | } 55 | } 56 | return nil 57 | } 58 | } 59 | 60 | var calendarComponents = CalendarComponents() 61 | 62 | init(day: String?, month: String?, year: String?) { 63 | self.day = day 64 | self.month = month 65 | self.year = year 66 | } 67 | 68 | func stringify() -> String { 69 | if let _day = day, let _month = month, let _year = year { 70 | return _day + " / " + _month + " / " + _year 71 | } 72 | return "" 73 | } 74 | } 75 | 76 | class AVCustomCalendarViewModel { 77 | 78 | var calendarComponents = CalendarComponents() 79 | let countOfMonthCells: Int = 12 80 | var date: _AVDate! 81 | var preSelectedDate: AVDate! 82 | 83 | init() { 84 | date = _AVDate(day: String(Calendar.current.component(.day, from: Date())), month: calendarComponents.months[Calendar.current.component(.month, from: Date()) - 1], year: String((Calendar.current.component(.year, from: Date()) - AGE_LIMIT))) 85 | } 86 | 87 | func getIndices(from date: AVDate) -> (day: Int, month: Int, year: Int) { 88 | var indices: (day: Int, month: Int, year: Int) = (0,0,0) 89 | indices.day = (Int(date.day ?? "1") ?? 1) - 1 90 | indices.month = calendarComponents.months.firstIndex(of: date.month ?? "Jan") ?? 0 91 | indices.year = calendarComponents.years.firstIndex(of: date.year ?? "Jan") ?? 0 92 | return indices 93 | } 94 | 95 | func getCurrentMonth() -> Int { 96 | let half = countOfMonthCells/2 97 | let currentMonthIndex = Calendar.current.component(.month, from: Date()) - 1 98 | let centerMonthIndex = half % calendarComponents.months.count 99 | let centerIndexToBeReturned = half - (centerMonthIndex - currentMonthIndex) 100 | return centerIndexToBeReturned 101 | } 102 | 103 | func getCurrentMonthIndex() -> Int { 104 | return (Calendar.current.component(.month, from: Date()) - 1) 105 | } 106 | 107 | func getCurrentDateIndex() -> Int { 108 | return (Calendar.current.component(.day, from: Date()) - 1) 109 | } 110 | 111 | func getCurrentYearIndex() -> Int { 112 | let years = calendarComponents.years 113 | let currentMonth = Calendar.current.component(.year, from: Date()) 114 | let index = years.firstIndex(of: "\(currentMonth)") 115 | return index! 116 | } 117 | 118 | func updateDate(dayValue day: Int? = nil, monthValue month: Int? = nil, yearValue year: Int? = nil) { 119 | if let day = day { 120 | date.day = String(day + 1) 121 | } 122 | if let month = month { 123 | date.month = calendarComponents.months[month % calendarComponents.months.count] 124 | } 125 | if let year = year { 126 | date.year = calendarComponents.years[year] 127 | } 128 | if let month = date.month, let year = date.year { 129 | updateTheDays(month: calendarComponents.months.firstIndex(of: month)! + 1, year: Int(year)!) 130 | } 131 | } 132 | 133 | private func updateTheDays(month monthValue: Int, year yearValue: Int) { 134 | let dateComponents = DateComponents(year: yearValue, month: monthValue) 135 | let calendar = Calendar.current 136 | let date = calendar.date(from: dateComponents)! 137 | let range = calendar.range(of: .day, in: .month, for: date)! 138 | let numDays = range.count 139 | calendarComponents.dates.value = (1...numDays).map { String($0) } 140 | } 141 | } 142 | 143 | class AVCustomCalendarController: UIViewController { 144 | 145 | internal var preSelectedDate: AVDate? 146 | 147 | private var _yearStyleComponents: CalendarComponentStyle? 148 | var yearStyleComponents: CalendarComponentStyle? { 149 | get { 150 | return _yearStyleComponents 151 | } set { 152 | _yearStyleComponents = newValue 153 | } 154 | } 155 | 156 | private var _monthStyleComponents: CalendarComponentStyle? 157 | var monthStyleComponents: CalendarComponentStyle? { 158 | get { 159 | return _monthStyleComponents 160 | } set { 161 | _monthStyleComponents = newValue 162 | } 163 | } 164 | 165 | private var _dateStyleComponents: CalendarComponentStyle? 166 | var dateStyleComponents: CalendarComponentStyle? { 167 | get { 168 | return _dateStyleComponents 169 | } set { 170 | _dateStyleComponents = newValue 171 | } 172 | } 173 | 174 | private lazy var dateHighlightImage: UIImageView = { 175 | let image = UIImageView(frame: CGRect(x: 0, y: 0, width: self.dateCollectionGrid.bounds.size.width*0.118, height: self.dateCollectionGrid.bounds.size.width*0.118)) 176 | image.layer.cornerRadius = image.bounds.size.height/2 177 | image.backgroundColor = _dateStyleComponents?.highlightColor 178 | return image 179 | }() 180 | 181 | @IBOutlet var yearSideShades: [UIImageView]! { 182 | didSet { 183 | let bundle = Bundle(for: AVCustomCalendarController.self) 184 | for view in yearSideShades { 185 | if view.tag == 100, let _image = UIImage(named: "calendar_left_year_gradient", in: bundle, compatibleWith: nil) { 186 | view.image = _image.withRenderingMode(.alwaysTemplate) 187 | } else if view.tag == 200, let _image = UIImage(named: "calendar_right_year_gradient", in: bundle, compatibleWith: nil) { 188 | view.image = _image.withRenderingMode(.alwaysTemplate) 189 | } 190 | view.tintColor = _yearStyleComponents?.backgroundColor 191 | } 192 | } 193 | } 194 | 195 | @IBOutlet var monthSideShades: [UIImageView]! { 196 | didSet { 197 | let bundle = Bundle(for: AVCustomCalendarController.self) 198 | for view in monthSideShades { 199 | if view.tag == 100, let _image = UIImage(named: "calendar_left_month_gradient", in: bundle, compatibleWith: nil) { 200 | view.image = _image.withRenderingMode(.alwaysTemplate) 201 | } else if view.tag == 200, let _image = UIImage(named: "calendar_right_month_gradient", in: bundle, compatibleWith: nil) { 202 | view.image = _image.withRenderingMode(.alwaysTemplate) 203 | } 204 | view.tintColor = _monthStyleComponents?.backgroundColor 205 | } 206 | } 207 | } 208 | 209 | @IBOutlet var yearCollectionGrid: AVHorizontalScrollCollectionView! { 210 | didSet { 211 | yearCollectionGrid.backgroundColor = _yearStyleComponents?.backgroundColor 212 | } 213 | } 214 | 215 | @IBOutlet var monthCollectionGrid: AVHorizontalScrollCollectionView! { 216 | didSet { 217 | monthCollectionGrid.backgroundColor = _monthStyleComponents?.backgroundColor 218 | } 219 | } 220 | 221 | @IBOutlet var dateCollectionGrid: AVHorizontalScrollCollectionView! { 222 | didSet { 223 | dateCollectionGrid.backgroundColor = _dateStyleComponents?.backgroundColor 224 | } 225 | } 226 | 227 | private let viewModel: AVCustomCalendarViewModel = AVCustomCalendarViewModel() 228 | 229 | override func viewDidLoad() { 230 | super.viewDidLoad() 231 | viewModel.preSelectedDate = preSelectedDate 232 | viewModel.calendarComponents.dates.bind = { [weak self] (arr) in 233 | guard let weakSelf = self else { return } 234 | if let day = weakSelf.viewModel.date.day { 235 | if Int(day)! > (arr?.count)! { 236 | weakSelf.dateHighlightImage.isHidden = true 237 | weakSelf.viewModel.date.day = nil 238 | } 239 | } 240 | weakSelf.dateCollectionGrid.reloadData() 241 | } 242 | } 243 | 244 | override func viewDidAppear(_ animated: Bool) { 245 | super.viewDidAppear(animated) 246 | var indices: (day: Int, month: Int, year: Int) = (0,0,0) 247 | if let preSelectedDate = preSelectedDate { 248 | indices.day = self.viewModel.getIndices(from: preSelectedDate).day 249 | indices.month = self.viewModel.getIndices(from: preSelectedDate).month 250 | indices.year = self.viewModel.getIndices(from: preSelectedDate).year 251 | } else { 252 | indices.day = self.viewModel.getCurrentDateIndex() 253 | indices.month = viewModel.getCurrentMonth() 254 | indices.year = self.viewModel.getCurrentYearIndex() 255 | } 256 | yearCollectionGrid.scrollToItem(at: IndexPath(row: indices.year, section: 0), at: .centeredHorizontally, animated: false) 257 | monthCollectionGrid.scrollToItem(at: IndexPath(row: indices.month, section: 0), at: .centeredHorizontally, animated: false) 258 | viewModel.updateDate() 259 | DispatchQueue.main.asyncAfter(deadline: .now() + 0.3) { 260 | self.updateCellTransform(with: CGAffineTransform(scaleX: 1.3, y: 1.3), cell: self.yearCollectionGrid.cellForItem(at: IndexPath(row: indices.year, section: 0)) as! AVCustomCalendarYearCell, withHighlightColor: self._yearStyleComponents?.highlightColor) 261 | self.updateCellTransform(with: CGAffineTransform(scaleX: 1.3, y: 1.3), cell: self.monthCollectionGrid.cellForItem(at: IndexPath(row: indices.month, section: 0)) as! AVCustomCalendarYearCell, withHighlightColor: self._monthStyleComponents?.highlightColor) 262 | let centerForCell = self.dateCollectionGrid.layoutAttributesForItem(at: IndexPath(row: indices.day, section: 0))?.center 263 | self.dateHighlightImage.center = centerForCell! 264 | self.dateCollectionGrid.addSubview(self.dateHighlightImage) 265 | self.dateHighlightImage.isHidden = false 266 | } 267 | } 268 | 269 | private func updateCellTransform(with transform: CGAffineTransform = CGAffineTransform.identity, cell aCell: AVCustomCalendarYearCell, withHighlightColor highlightColor: UIColor? = .white) { 270 | UIView.animate(withDuration: 0.2) { 271 | aCell.transform = transform 272 | if transform != .identity { 273 | aCell.titleLabel.textColor = highlightColor 274 | } 275 | } 276 | } 277 | 278 | func getDate() -> AVDate? { 279 | if let _ = viewModel.date.doubleVal { //Calculate double value. 280 | var date = AVDate() 281 | date.day = viewModel.date.day 282 | date.month = viewModel.date.month 283 | date.year = viewModel.date.year 284 | date.doubleVal = viewModel.date.doubleVal 285 | return date 286 | } 287 | return nil 288 | } 289 | } 290 | 291 | extension AVCustomCalendarController: UICollectionViewDelegate { 292 | func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath) { 293 | if collectionView == dateCollectionGrid { 294 | let centerForCell = collectionView.layoutAttributesForItem(at: indexPath)?.center 295 | self.dateHighlightImage.isHidden = false 296 | dateHighlightImage.center = centerForCell! 297 | viewModel.updateDate(dayValue: indexPath.row) 298 | } 299 | } 300 | } 301 | 302 | extension AVCustomCalendarController: UICollectionViewDataSource { 303 | 304 | func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int { 305 | if collectionView == yearCollectionGrid { 306 | return viewModel.calendarComponents.years.count 307 | } else if collectionView == monthCollectionGrid { 308 | return viewModel.countOfMonthCells 309 | } else if collectionView == dateCollectionGrid { 310 | return viewModel.calendarComponents.masterDates.value!.count 311 | } 312 | return 0 313 | } 314 | 315 | func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell { 316 | let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "cell", for: indexPath) as! AVCustomCalendarYearCell 317 | if collectionView == yearCollectionGrid { 318 | cell.titleLabel.text = viewModel.calendarComponents.years[indexPath.row] 319 | cell.titleLabel.textColor = _yearStyleComponents?.textColor 320 | } else if collectionView == monthCollectionGrid { 321 | let itemToShow = viewModel.calendarComponents.months[indexPath.row % viewModel.calendarComponents.months.count] 322 | cell.titleLabel.text = itemToShow 323 | cell.titleLabel.textColor = _monthStyleComponents?.textColor 324 | } else if collectionView == dateCollectionGrid { 325 | cell.titleLabel.text = viewModel.calendarComponents.masterDates.value![indexPath.row] 326 | cell.titleLabel.textColor = _dateStyleComponents?.textColor 327 | if indexPath.row >= viewModel.calendarComponents.dates.value?.count ?? 0 { 328 | cell.titleLabel.textColor = cell.titleLabel.textColor.withAlphaComponent(0.5) 329 | cell.isUserInteractionEnabled = false 330 | } else { 331 | cell.isUserInteractionEnabled = true 332 | } 333 | } 334 | return cell 335 | } 336 | } 337 | 338 | extension AVCustomCalendarController: UICollectionViewDelegateFlowLayout { 339 | func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize { 340 | if collectionView == dateCollectionGrid { 341 | return CGSize(width: (collectionView.bounds.width*0.136), height: (collectionView.bounds.height*0.086)) 342 | } else if collectionView == monthCollectionGrid { 343 | return CGSize(width: 63.0, height: 30.0) 344 | } else if collectionView == yearCollectionGrid { 345 | return CGSize(width: 63.0, height: 30.0) 346 | } 347 | return .zero 348 | } 349 | 350 | func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, minimumLineSpacingForSectionAt section: Int) -> CGFloat { 351 | if collectionView == dateCollectionGrid { 352 | return collectionView.bounds.size.width * 0.08 353 | } 354 | return 10 355 | } 356 | 357 | func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, insetForSectionAt section: Int) -> UIEdgeInsets { 358 | if collectionView == dateCollectionGrid { 359 | return UIEdgeInsets(top: collectionView.bounds.size.width * 0.04, left: collectionView.bounds.size.width * 0.012, bottom: collectionView.bounds.size.width * 0.04, right: collectionView.bounds.size.width * 0.012) 360 | } else if collectionView == yearCollectionGrid { 361 | return UIEdgeInsets(top: (collectionView.bounds.size.height - (collectionView.bounds.height*0.086))/2, left: 15, bottom: (collectionView.bounds.size.height - (collectionView.bounds.height*0.086))/2, right: (collectionView.bounds.size.width - (collectionView.bounds.width*0.136))/2) 362 | } else if collectionView == monthCollectionGrid { 363 | return UIEdgeInsets(top: 0, left: (collectionView.bounds.size.width - (collectionView.bounds.width*0.136))/2, bottom: 0, right: (collectionView.bounds.size.width - (collectionView.bounds.width*0.136))/2) 364 | } 365 | return .zero 366 | } 367 | } 368 | 369 | extension AVCustomCalendarController: UIScrollViewDelegate { 370 | 371 | func scrollViewWillBeginDragging(_ scrollView: UIScrollView) { 372 | if scrollView.tag == 101 { 373 | resetCellApperence(for: yearCollectionGrid) 374 | } else if scrollView.tag == 102 { 375 | resetCellApperence(for: monthCollectionGrid) 376 | } 377 | } 378 | 379 | func scrollViewDidEndDecelerating(_ scrollView: UIScrollView) { 380 | if scrollView.tag == 101 { 381 | scrollToNearestCenterIndex(for: yearCollectionGrid) 382 | } else if scrollView.tag == 102 { 383 | scrollToNearestCenterIndex(for: monthCollectionGrid) 384 | } 385 | } 386 | 387 | func scrollViewDidEndDragging(_ scrollView: UIScrollView, willDecelerate decelerate: Bool) { 388 | if !decelerate { 389 | if scrollView.tag == 101 { 390 | scrollToNearestCenterIndex(for: yearCollectionGrid) 391 | } else if scrollView.tag == 102 { 392 | scrollToNearestCenterIndex(for: monthCollectionGrid) 393 | } 394 | } 395 | } 396 | 397 | func resetCellApperence(for collectionView: AVHorizontalScrollCollectionView) { 398 | for cell: AVCustomCalendarYearCell in collectionView.visibleCells as! [AVCustomCalendarYearCell] { 399 | updateCellTransform(cell: cell) 400 | if collectionView == yearCollectionGrid { 401 | cell.titleLabel.textColor = _yearStyleComponents?.textColor 402 | } else if collectionView == monthCollectionGrid { 403 | cell.titleLabel.textColor = _monthStyleComponents?.textColor 404 | } 405 | } 406 | } 407 | 408 | func scrollToNearestCenterIndex(for collectionView: AVHorizontalScrollCollectionView) { 409 | 410 | var closestCell : UICollectionViewCell = collectionView.visibleCells[0]; 411 | for cell in collectionView.visibleCells as! [AVCustomCalendarYearCell] { 412 | updateCellTransform(cell: cell) 413 | let closestCellDelta = abs(closestCell.center.x - collectionView.bounds.size.width/2.0 - collectionView.contentOffset.x) 414 | let cellDelta = abs(cell.center.x - collectionView.bounds.size.width/2.0 - collectionView.contentOffset.x) 415 | if (cellDelta < closestCellDelta){ 416 | closestCell = cell 417 | } 418 | } 419 | if collectionView == yearCollectionGrid { 420 | updateCellTransform(with: CGAffineTransform(scaleX: 1.3, y: 1.3), cell: closestCell as! AVCustomCalendarYearCell, withHighlightColor: _yearStyleComponents?.highlightColor) 421 | } else if collectionView == monthCollectionGrid { 422 | updateCellTransform(with: CGAffineTransform(scaleX: 1.3, y: 1.3), cell: closestCell as! AVCustomCalendarYearCell, withHighlightColor: _monthStyleComponents?.highlightColor) 423 | } 424 | let indexPath = collectionView.indexPath(for: closestCell) 425 | collectionView.scrollToItem(at: indexPath!, at: UICollectionView.ScrollPosition.centeredHorizontally, animated: true) 426 | if let indexPath = indexPath { 427 | if collectionView == yearCollectionGrid { 428 | viewModel.updateDate(yearValue: indexPath.row) 429 | } else if collectionView == monthCollectionGrid { 430 | viewModel.updateDate(monthValue: indexPath.row) 431 | } 432 | } 433 | } 434 | } 435 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/APCustomCalenderCells/APCustomCalendarYearCell.swift: -------------------------------------------------------------------------------- 1 | // 2 | // AVCustomCalendarYearCell.swift 3 | // Anirudh Vyas 4 | // 5 | // Created by Anirudh on 06/05/19. 6 | // Copyright © 2019 Anirudh Vyas. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | class AVCustomCalendarYearCell: UICollectionViewCell { 12 | @IBOutlet weak var titleLabel: UILabel! 13 | } 14 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/APHorizontalScrollCollectionView.swift: -------------------------------------------------------------------------------- 1 | // 2 | // AVHorizontalScrollCollectionView.swift 3 | // Anirudh Vyas 4 | // 5 | // Created by Anirudh on 06/05/19. 6 | // Copyright © 2019 Anirudh Vyas. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | class AVHorizontalScrollCollectionView: UICollectionView { 12 | 13 | 14 | } 15 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/Calendar.storyboard: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | 94 | 95 | 96 | 97 | 98 | 99 | 100 | 101 | 102 | 103 | 104 | 105 | 106 | 107 | 108 | 109 | 110 | 111 | 112 | 113 | 114 | 115 | 116 | 117 | 118 | 119 | 120 | 121 | 122 | 123 | 124 | 125 | 126 | 127 | 128 | 129 | 130 | 131 | 132 | 138 | 139 | 140 | 141 | 142 | 143 | 144 | 145 | 146 | 147 | 148 | 149 | 150 | 151 | 152 | 153 | 154 | 155 | 156 | 157 | 158 | 159 | 160 | 161 | 162 | 163 | 164 | 165 | 166 | 167 | 168 | 169 | 170 | 171 | 172 | 173 | 174 | 175 | 176 | 182 | 183 | 184 | 185 | 186 | 187 | 188 | 189 | 190 | 191 | 192 | 193 | 194 | 195 | 196 | 197 | 198 | 199 | 200 | 201 | 202 | 203 | 204 | 205 | 206 | 207 | 208 | 209 | 210 | 211 | 212 | 213 | 214 | 215 | 216 | 217 | 223 | 224 | 225 | 226 | 227 | 228 | 229 | 230 | 231 | 232 | 233 | 234 | 235 | 236 | 237 | 238 | 239 | 240 | 241 | 242 | 243 | 244 | 245 | 246 | 247 | 248 | 249 | 250 | 251 | 252 | 253 | 254 | 255 | 256 | 257 | 258 | 259 | 260 | 261 | 262 | 263 | 264 | 265 | 266 | 267 | 268 | 269 | 270 | 271 | 272 | 273 | 274 | 275 | 276 | 277 | 278 | 279 | 280 | 281 | 282 | 283 | 284 | 285 | 286 | 287 | 288 | 289 | 290 | 291 | 292 | 293 | 294 | 295 | 296 | 297 | 298 | 299 | 300 | 301 | 302 | 303 | 304 | 305 | 306 | 307 | 308 | 309 | 310 | 311 | 312 | 313 | 314 | 315 | 316 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_check.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "filename" : "calendar_check.png", 6 | "scale" : "1x" 7 | }, 8 | { 9 | "idiom" : "universal", 10 | "filename" : "calendar_check@2x.png", 11 | "scale" : "2x" 12 | }, 13 | { 14 | "idiom" : "universal", 15 | "filename" : "calendar_check@3x.png", 16 | "scale" : "3x" 17 | } 18 | ], 19 | "info" : { 20 | "version" : 1, 21 | "author" : "xcode" 22 | } 23 | } -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_check.imageset/calendar_check.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_check.imageset/calendar_check.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_check.imageset/calendar_check@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_check.imageset/calendar_check@2x.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_check.imageset/calendar_check@3x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_check.imageset/calendar_check@3x.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_left_month_gradient.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "filename" : "calendar_left_month_gradient.png", 6 | "scale" : "1x" 7 | }, 8 | { 9 | "idiom" : "universal", 10 | "filename" : "calendar_left_month_gradient@2x.png", 11 | "scale" : "2x" 12 | }, 13 | { 14 | "idiom" : "universal", 15 | "filename" : "calendar_left_month_gradient@3x.png", 16 | "scale" : "3x" 17 | } 18 | ], 19 | "info" : { 20 | "version" : 1, 21 | "author" : "xcode" 22 | } 23 | } -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_left_month_gradient.imageset/calendar_left_month_gradient.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_left_month_gradient.imageset/calendar_left_month_gradient.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_left_month_gradient.imageset/calendar_left_month_gradient@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_left_month_gradient.imageset/calendar_left_month_gradient@2x.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_left_month_gradient.imageset/calendar_left_month_gradient@3x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_left_month_gradient.imageset/calendar_left_month_gradient@3x.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_left_year_gradient.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "filename" : "calendar_left_year_gradient.png", 6 | "scale" : "1x" 7 | }, 8 | { 9 | "idiom" : "universal", 10 | "filename" : "calendar_left_year_gradient@2x.png", 11 | "scale" : "2x" 12 | }, 13 | { 14 | "idiom" : "universal", 15 | "filename" : "calendar_left_year_gradient@3x.png", 16 | "scale" : "3x" 17 | } 18 | ], 19 | "info" : { 20 | "version" : 1, 21 | "author" : "xcode" 22 | } 23 | } -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_left_year_gradient.imageset/calendar_left_year_gradient.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_left_year_gradient.imageset/calendar_left_year_gradient.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_left_year_gradient.imageset/calendar_left_year_gradient@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_left_year_gradient.imageset/calendar_left_year_gradient@2x.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_left_year_gradient.imageset/calendar_left_year_gradient@3x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_left_year_gradient.imageset/calendar_left_year_gradient@3x.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_partition.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "filename" : "calendar_partition.png", 6 | "scale" : "1x" 7 | }, 8 | { 9 | "idiom" : "universal", 10 | "filename" : "calendar_partition@2x.png", 11 | "scale" : "2x" 12 | }, 13 | { 14 | "idiom" : "universal", 15 | "filename" : "calendar_partition@3x.png", 16 | "scale" : "3x" 17 | } 18 | ], 19 | "info" : { 20 | "version" : 1, 21 | "author" : "xcode" 22 | } 23 | } -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_partition.imageset/calendar_partition.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_partition.imageset/calendar_partition.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_partition.imageset/calendar_partition@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_partition.imageset/calendar_partition@2x.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_partition.imageset/calendar_partition@3x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_partition.imageset/calendar_partition@3x.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_right_month_gradient.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "filename" : "calendar_right_month_gradient.png", 6 | "scale" : "1x" 7 | }, 8 | { 9 | "idiom" : "universal", 10 | "filename" : "calendar_right_month_gradient@2x.png", 11 | "scale" : "2x" 12 | }, 13 | { 14 | "idiom" : "universal", 15 | "filename" : "calendar_right_month_gradient@3x.png", 16 | "scale" : "3x" 17 | } 18 | ], 19 | "info" : { 20 | "version" : 1, 21 | "author" : "xcode" 22 | } 23 | } -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_right_month_gradient.imageset/calendar_right_month_gradient.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_right_month_gradient.imageset/calendar_right_month_gradient.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_right_month_gradient.imageset/calendar_right_month_gradient@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_right_month_gradient.imageset/calendar_right_month_gradient@2x.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_right_month_gradient.imageset/calendar_right_month_gradient@3x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_right_month_gradient.imageset/calendar_right_month_gradient@3x.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_right_year_gradient.imageset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "universal", 5 | "filename" : "calendar_right_year_gradient.png", 6 | "scale" : "1x" 7 | }, 8 | { 9 | "idiom" : "universal", 10 | "filename" : "calendar_right_year_gradient@2x.png", 11 | "scale" : "2x" 12 | }, 13 | { 14 | "idiom" : "universal", 15 | "filename" : "calendar_right_year_gradient@3x.png", 16 | "scale" : "3x" 17 | } 18 | ], 19 | "info" : { 20 | "version" : 1, 21 | "author" : "xcode" 22 | } 23 | } -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_right_year_gradient.imageset/calendar_right_year_gradient.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_right_year_gradient.imageset/calendar_right_year_gradient.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_right_year_gradient.imageset/calendar_right_year_gradient@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_right_year_gradient.imageset/calendar_right_year_gradient@2x.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_right_year_gradient.imageset/calendar_right_year_gradient@3x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendar/CustomCalendarController/CalendarAssets.xcassets/calendar_right_year_gradient.imageset/calendar_right_year_gradient@3x.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/DynamicType/APDynamicType.swift: -------------------------------------------------------------------------------- 1 | // 2 | // DynamicType.swift 3 | // Anirudh Vyas 4 | // 5 | // Created by Anirudh on 10/03/19. 6 | // Copyright © 2019 Anirudh Vyas. All rights reserved. 7 | // 8 | 9 | import Foundation 10 | 11 | class Dynamic { 12 | 13 | var value: T? { 14 | didSet { 15 | bind?(value) 16 | } 17 | } 18 | 19 | var bind: ((T?)->())? 20 | 21 | init(_ _value: T) { 22 | value = _value 23 | } 24 | } 25 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendar/Protocols/HapticFeedbackGenerator.swift: -------------------------------------------------------------------------------- 1 | // 2 | // HapticFeedbackGenerator.swift 3 | // AVCalendarSample 4 | // 5 | // Created by Anirudh on 30/09/19. 6 | // Copyright © 2019 Postagic. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | public protocol HapticFeedback { 12 | func generateFeedback() 13 | } 14 | 15 | extension UIControl: HapticFeedback { } 16 | 17 | public extension HapticFeedback where Self: UIControl { 18 | func generateFeedback() { 19 | if #available(iOS 10.0, *) { 20 | let generator = UIImpactFeedbackGenerator(style: .light) 21 | generator.impactOccurred() 22 | } 23 | } 24 | } 25 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendarSample.xcodeproj/project.pbxproj: -------------------------------------------------------------------------------- 1 | // !$*UTF8*$! 2 | { 3 | archiveVersion = 1; 4 | classes = { 5 | }; 6 | objectVersion = 50; 7 | objects = { 8 | 9 | /* Begin PBXBuildFile section */ 10 | 173925B5231303F300EFC5C3 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 173925B4231303F300EFC5C3 /* AppDelegate.swift */; }; 11 | 173925B7231303F300EFC5C3 /* ViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 173925B6231303F300EFC5C3 /* ViewController.swift */; }; 12 | 173925BA231303F300EFC5C3 /* Main.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 173925B8231303F300EFC5C3 /* Main.storyboard */; }; 13 | 173925BC231303F400EFC5C3 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 173925BB231303F400EFC5C3 /* Assets.xcassets */; }; 14 | 173925BF231303F400EFC5C3 /* LaunchScreen.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 173925BD231303F400EFC5C3 /* LaunchScreen.storyboard */; }; 15 | 173925CA231303F400EFC5C3 /* AVCalendarSampleTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 173925C9231303F400EFC5C3 /* AVCalendarSampleTests.swift */; }; 16 | 173925D5231303F400EFC5C3 /* AVCalendarSampleUITests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 173925D4231303F400EFC5C3 /* AVCalendarSampleUITests.swift */; }; 17 | 17594C0E233B0B710010AB9B /* APDynamicType.swift in Sources */ = {isa = PBXBuildFile; fileRef = 17594C05233B0B710010AB9B /* APDynamicType.swift */; }; 18 | 17594C0F233B0B710010AB9B /* APHorizontalScrollCollectionView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 17594C07233B0B710010AB9B /* APHorizontalScrollCollectionView.swift */; }; 19 | 17594C10233B0B710010AB9B /* APCalendarViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 17594C08233B0B710010AB9B /* APCalendarViewController.swift */; }; 20 | 17594C11233B0B710010AB9B /* Calendar.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 17594C09233B0B710010AB9B /* Calendar.storyboard */; }; 21 | 17594C12233B0B710010AB9B /* APCustomCalendarYearCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = 17594C0B233B0B710010AB9B /* APCustomCalendarYearCell.swift */; }; 22 | 17594C13233B0B710010AB9B /* APCustomCalendarContainer.swift in Sources */ = {isa = PBXBuildFile; fileRef = 17594C0C233B0B710010AB9B /* APCustomCalendarContainer.swift */; }; 23 | 17594C14233B0B710010AB9B /* CalendarAssets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 17594C0D233B0B710010AB9B /* CalendarAssets.xcassets */; }; 24 | 17D8AD8D2341E4EB00730E56 /* HapticFeedbackGenerator.swift in Sources */ = {isa = PBXBuildFile; fileRef = 17D8AD8C2341E4EB00730E56 /* HapticFeedbackGenerator.swift */; }; 25 | /* End PBXBuildFile section */ 26 | 27 | /* Begin PBXContainerItemProxy section */ 28 | 173925C6231303F400EFC5C3 /* PBXContainerItemProxy */ = { 29 | isa = PBXContainerItemProxy; 30 | containerPortal = 173925A9231303F300EFC5C3 /* Project object */; 31 | proxyType = 1; 32 | remoteGlobalIDString = 173925B0231303F300EFC5C3; 33 | remoteInfo = AVCalendarSample; 34 | }; 35 | 173925D1231303F400EFC5C3 /* PBXContainerItemProxy */ = { 36 | isa = PBXContainerItemProxy; 37 | containerPortal = 173925A9231303F300EFC5C3 /* Project object */; 38 | proxyType = 1; 39 | remoteGlobalIDString = 173925B0231303F300EFC5C3; 40 | remoteInfo = AVCalendarSample; 41 | }; 42 | /* End PBXContainerItemProxy section */ 43 | 44 | /* Begin PBXFileReference section */ 45 | 173925B1231303F300EFC5C3 /* AVCalendarSample.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = AVCalendarSample.app; sourceTree = BUILT_PRODUCTS_DIR; }; 46 | 173925B4231303F300EFC5C3 /* AppDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = ""; }; 47 | 173925B6231303F300EFC5C3 /* ViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ViewController.swift; sourceTree = ""; }; 48 | 173925B9231303F300EFC5C3 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/Main.storyboard; sourceTree = ""; }; 49 | 173925BB231303F400EFC5C3 /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = ""; }; 50 | 173925BE231303F400EFC5C3 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/LaunchScreen.storyboard; sourceTree = ""; }; 51 | 173925C0231303F400EFC5C3 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 52 | 173925C5231303F400EFC5C3 /* AVCalendarSampleTests.xctest */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = AVCalendarSampleTests.xctest; sourceTree = BUILT_PRODUCTS_DIR; }; 53 | 173925C9231303F400EFC5C3 /* AVCalendarSampleTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AVCalendarSampleTests.swift; sourceTree = ""; }; 54 | 173925CB231303F400EFC5C3 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 55 | 173925D0231303F400EFC5C3 /* AVCalendarSampleUITests.xctest */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = AVCalendarSampleUITests.xctest; sourceTree = BUILT_PRODUCTS_DIR; }; 56 | 173925D4231303F400EFC5C3 /* AVCalendarSampleUITests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AVCalendarSampleUITests.swift; sourceTree = ""; }; 57 | 173925D6231303F400EFC5C3 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 58 | 17594C05233B0B710010AB9B /* APDynamicType.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = APDynamicType.swift; sourceTree = ""; }; 59 | 17594C07233B0B710010AB9B /* APHorizontalScrollCollectionView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = APHorizontalScrollCollectionView.swift; sourceTree = ""; }; 60 | 17594C08233B0B710010AB9B /* APCalendarViewController.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = APCalendarViewController.swift; sourceTree = ""; }; 61 | 17594C09233B0B710010AB9B /* Calendar.storyboard */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = file.storyboard; path = Calendar.storyboard; sourceTree = ""; }; 62 | 17594C0B233B0B710010AB9B /* APCustomCalendarYearCell.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = APCustomCalendarYearCell.swift; sourceTree = ""; }; 63 | 17594C0C233B0B710010AB9B /* APCustomCalendarContainer.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = APCustomCalendarContainer.swift; sourceTree = ""; }; 64 | 17594C0D233B0B710010AB9B /* CalendarAssets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = CalendarAssets.xcassets; sourceTree = ""; }; 65 | 17D8AD8C2341E4EB00730E56 /* HapticFeedbackGenerator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = HapticFeedbackGenerator.swift; sourceTree = ""; }; 66 | /* End PBXFileReference section */ 67 | 68 | /* Begin PBXFrameworksBuildPhase section */ 69 | 173925AE231303F300EFC5C3 /* Frameworks */ = { 70 | isa = PBXFrameworksBuildPhase; 71 | buildActionMask = 2147483647; 72 | files = ( 73 | ); 74 | runOnlyForDeploymentPostprocessing = 0; 75 | }; 76 | 173925C2231303F400EFC5C3 /* Frameworks */ = { 77 | isa = PBXFrameworksBuildPhase; 78 | buildActionMask = 2147483647; 79 | files = ( 80 | ); 81 | runOnlyForDeploymentPostprocessing = 0; 82 | }; 83 | 173925CD231303F400EFC5C3 /* Frameworks */ = { 84 | isa = PBXFrameworksBuildPhase; 85 | buildActionMask = 2147483647; 86 | files = ( 87 | ); 88 | runOnlyForDeploymentPostprocessing = 0; 89 | }; 90 | /* End PBXFrameworksBuildPhase section */ 91 | 92 | /* Begin PBXGroup section */ 93 | 173925A8231303F300EFC5C3 = { 94 | isa = PBXGroup; 95 | children = ( 96 | 17594C03233B0B710010AB9B /* AVCalendar */, 97 | 173925B3231303F300EFC5C3 /* AVCalendarSample */, 98 | 173925C8231303F400EFC5C3 /* AVCalendarSampleTests */, 99 | 173925D3231303F400EFC5C3 /* AVCalendarSampleUITests */, 100 | 173925B2231303F300EFC5C3 /* Products */, 101 | 4C33B577FB31A4D20C6739F1 /* Pods */, 102 | ); 103 | sourceTree = ""; 104 | }; 105 | 173925B2231303F300EFC5C3 /* Products */ = { 106 | isa = PBXGroup; 107 | children = ( 108 | 173925B1231303F300EFC5C3 /* AVCalendarSample.app */, 109 | 173925C5231303F400EFC5C3 /* AVCalendarSampleTests.xctest */, 110 | 173925D0231303F400EFC5C3 /* AVCalendarSampleUITests.xctest */, 111 | ); 112 | name = Products; 113 | sourceTree = ""; 114 | }; 115 | 173925B3231303F300EFC5C3 /* AVCalendarSample */ = { 116 | isa = PBXGroup; 117 | children = ( 118 | 173925B4231303F300EFC5C3 /* AppDelegate.swift */, 119 | 173925B6231303F300EFC5C3 /* ViewController.swift */, 120 | 173925B8231303F300EFC5C3 /* Main.storyboard */, 121 | 173925BB231303F400EFC5C3 /* Assets.xcassets */, 122 | 173925BD231303F400EFC5C3 /* LaunchScreen.storyboard */, 123 | 173925C0231303F400EFC5C3 /* Info.plist */, 124 | ); 125 | path = AVCalendarSample; 126 | sourceTree = ""; 127 | }; 128 | 173925C8231303F400EFC5C3 /* AVCalendarSampleTests */ = { 129 | isa = PBXGroup; 130 | children = ( 131 | 173925C9231303F400EFC5C3 /* AVCalendarSampleTests.swift */, 132 | 173925CB231303F400EFC5C3 /* Info.plist */, 133 | ); 134 | path = AVCalendarSampleTests; 135 | sourceTree = ""; 136 | }; 137 | 173925D3231303F400EFC5C3 /* AVCalendarSampleUITests */ = { 138 | isa = PBXGroup; 139 | children = ( 140 | 173925D4231303F400EFC5C3 /* AVCalendarSampleUITests.swift */, 141 | 173925D6231303F400EFC5C3 /* Info.plist */, 142 | ); 143 | path = AVCalendarSampleUITests; 144 | sourceTree = ""; 145 | }; 146 | 17594C03233B0B710010AB9B /* AVCalendar */ = { 147 | isa = PBXGroup; 148 | children = ( 149 | 17D8AD8B2341E4D200730E56 /* Protocols */, 150 | 17594C04233B0B710010AB9B /* DynamicType */, 151 | 17594C06233B0B710010AB9B /* CustomCalendarController */, 152 | ); 153 | path = AVCalendar; 154 | sourceTree = ""; 155 | }; 156 | 17594C04233B0B710010AB9B /* DynamicType */ = { 157 | isa = PBXGroup; 158 | children = ( 159 | 17594C05233B0B710010AB9B /* APDynamicType.swift */, 160 | ); 161 | path = DynamicType; 162 | sourceTree = ""; 163 | }; 164 | 17594C06233B0B710010AB9B /* CustomCalendarController */ = { 165 | isa = PBXGroup; 166 | children = ( 167 | 17594C07233B0B710010AB9B /* APHorizontalScrollCollectionView.swift */, 168 | 17594C08233B0B710010AB9B /* APCalendarViewController.swift */, 169 | 17594C09233B0B710010AB9B /* Calendar.storyboard */, 170 | 17594C0A233B0B710010AB9B /* APCustomCalenderCells */, 171 | 17594C0C233B0B710010AB9B /* APCustomCalendarContainer.swift */, 172 | 17594C0D233B0B710010AB9B /* CalendarAssets.xcassets */, 173 | ); 174 | path = CustomCalendarController; 175 | sourceTree = ""; 176 | }; 177 | 17594C0A233B0B710010AB9B /* APCustomCalenderCells */ = { 178 | isa = PBXGroup; 179 | children = ( 180 | 17594C0B233B0B710010AB9B /* APCustomCalendarYearCell.swift */, 181 | ); 182 | path = APCustomCalenderCells; 183 | sourceTree = ""; 184 | }; 185 | 17D8AD8B2341E4D200730E56 /* Protocols */ = { 186 | isa = PBXGroup; 187 | children = ( 188 | 17D8AD8C2341E4EB00730E56 /* HapticFeedbackGenerator.swift */, 189 | ); 190 | path = Protocols; 191 | sourceTree = ""; 192 | }; 193 | 4C33B577FB31A4D20C6739F1 /* Pods */ = { 194 | isa = PBXGroup; 195 | children = ( 196 | ); 197 | path = Pods; 198 | sourceTree = ""; 199 | }; 200 | /* End PBXGroup section */ 201 | 202 | /* Begin PBXNativeTarget section */ 203 | 173925B0231303F300EFC5C3 /* AVCalendarSample */ = { 204 | isa = PBXNativeTarget; 205 | buildConfigurationList = 173925D9231303F400EFC5C3 /* Build configuration list for PBXNativeTarget "AVCalendarSample" */; 206 | buildPhases = ( 207 | 173925AD231303F300EFC5C3 /* Sources */, 208 | 173925AE231303F300EFC5C3 /* Frameworks */, 209 | 173925AF231303F300EFC5C3 /* Resources */, 210 | ); 211 | buildRules = ( 212 | ); 213 | dependencies = ( 214 | ); 215 | name = AVCalendarSample; 216 | productName = AVCalendarSample; 217 | productReference = 173925B1231303F300EFC5C3 /* AVCalendarSample.app */; 218 | productType = "com.apple.product-type.application"; 219 | }; 220 | 173925C4231303F400EFC5C3 /* AVCalendarSampleTests */ = { 221 | isa = PBXNativeTarget; 222 | buildConfigurationList = 173925DC231303F400EFC5C3 /* Build configuration list for PBXNativeTarget "AVCalendarSampleTests" */; 223 | buildPhases = ( 224 | 173925C1231303F400EFC5C3 /* Sources */, 225 | 173925C2231303F400EFC5C3 /* Frameworks */, 226 | 173925C3231303F400EFC5C3 /* Resources */, 227 | ); 228 | buildRules = ( 229 | ); 230 | dependencies = ( 231 | 173925C7231303F400EFC5C3 /* PBXTargetDependency */, 232 | ); 233 | name = AVCalendarSampleTests; 234 | productName = AVCalendarSampleTests; 235 | productReference = 173925C5231303F400EFC5C3 /* AVCalendarSampleTests.xctest */; 236 | productType = "com.apple.product-type.bundle.unit-test"; 237 | }; 238 | 173925CF231303F400EFC5C3 /* AVCalendarSampleUITests */ = { 239 | isa = PBXNativeTarget; 240 | buildConfigurationList = 173925DF231303F400EFC5C3 /* Build configuration list for PBXNativeTarget "AVCalendarSampleUITests" */; 241 | buildPhases = ( 242 | 173925CC231303F400EFC5C3 /* Sources */, 243 | 173925CD231303F400EFC5C3 /* Frameworks */, 244 | 173925CE231303F400EFC5C3 /* Resources */, 245 | ); 246 | buildRules = ( 247 | ); 248 | dependencies = ( 249 | 173925D2231303F400EFC5C3 /* PBXTargetDependency */, 250 | ); 251 | name = AVCalendarSampleUITests; 252 | productName = AVCalendarSampleUITests; 253 | productReference = 173925D0231303F400EFC5C3 /* AVCalendarSampleUITests.xctest */; 254 | productType = "com.apple.product-type.bundle.ui-testing"; 255 | }; 256 | /* End PBXNativeTarget section */ 257 | 258 | /* Begin PBXProject section */ 259 | 173925A9231303F300EFC5C3 /* Project object */ = { 260 | isa = PBXProject; 261 | attributes = { 262 | LastSwiftUpdateCheck = 1020; 263 | LastUpgradeCheck = 1020; 264 | ORGANIZATIONNAME = Postagic; 265 | TargetAttributes = { 266 | 173925B0231303F300EFC5C3 = { 267 | CreatedOnToolsVersion = 10.2.1; 268 | }; 269 | 173925C4231303F400EFC5C3 = { 270 | CreatedOnToolsVersion = 10.2.1; 271 | TestTargetID = 173925B0231303F300EFC5C3; 272 | }; 273 | 173925CF231303F400EFC5C3 = { 274 | CreatedOnToolsVersion = 10.2.1; 275 | TestTargetID = 173925B0231303F300EFC5C3; 276 | }; 277 | }; 278 | }; 279 | buildConfigurationList = 173925AC231303F300EFC5C3 /* Build configuration list for PBXProject "AVCalendarSample" */; 280 | compatibilityVersion = "Xcode 9.3"; 281 | developmentRegion = en; 282 | hasScannedForEncodings = 0; 283 | knownRegions = ( 284 | en, 285 | Base, 286 | ); 287 | mainGroup = 173925A8231303F300EFC5C3; 288 | productRefGroup = 173925B2231303F300EFC5C3 /* Products */; 289 | projectDirPath = ""; 290 | projectRoot = ""; 291 | targets = ( 292 | 173925B0231303F300EFC5C3 /* AVCalendarSample */, 293 | 173925C4231303F400EFC5C3 /* AVCalendarSampleTests */, 294 | 173925CF231303F400EFC5C3 /* AVCalendarSampleUITests */, 295 | ); 296 | }; 297 | /* End PBXProject section */ 298 | 299 | /* Begin PBXResourcesBuildPhase section */ 300 | 173925AF231303F300EFC5C3 /* Resources */ = { 301 | isa = PBXResourcesBuildPhase; 302 | buildActionMask = 2147483647; 303 | files = ( 304 | 17594C11233B0B710010AB9B /* Calendar.storyboard in Resources */, 305 | 17594C14233B0B710010AB9B /* CalendarAssets.xcassets in Resources */, 306 | 173925BF231303F400EFC5C3 /* LaunchScreen.storyboard in Resources */, 307 | 173925BC231303F400EFC5C3 /* Assets.xcassets in Resources */, 308 | 173925BA231303F300EFC5C3 /* Main.storyboard in Resources */, 309 | ); 310 | runOnlyForDeploymentPostprocessing = 0; 311 | }; 312 | 173925C3231303F400EFC5C3 /* Resources */ = { 313 | isa = PBXResourcesBuildPhase; 314 | buildActionMask = 2147483647; 315 | files = ( 316 | ); 317 | runOnlyForDeploymentPostprocessing = 0; 318 | }; 319 | 173925CE231303F400EFC5C3 /* Resources */ = { 320 | isa = PBXResourcesBuildPhase; 321 | buildActionMask = 2147483647; 322 | files = ( 323 | ); 324 | runOnlyForDeploymentPostprocessing = 0; 325 | }; 326 | /* End PBXResourcesBuildPhase section */ 327 | 328 | /* Begin PBXSourcesBuildPhase section */ 329 | 173925AD231303F300EFC5C3 /* Sources */ = { 330 | isa = PBXSourcesBuildPhase; 331 | buildActionMask = 2147483647; 332 | files = ( 333 | 17594C12233B0B710010AB9B /* APCustomCalendarYearCell.swift in Sources */, 334 | 173925B7231303F300EFC5C3 /* ViewController.swift in Sources */, 335 | 173925B5231303F300EFC5C3 /* AppDelegate.swift in Sources */, 336 | 17594C13233B0B710010AB9B /* APCustomCalendarContainer.swift in Sources */, 337 | 17594C0F233B0B710010AB9B /* APHorizontalScrollCollectionView.swift in Sources */, 338 | 17D8AD8D2341E4EB00730E56 /* HapticFeedbackGenerator.swift in Sources */, 339 | 17594C0E233B0B710010AB9B /* APDynamicType.swift in Sources */, 340 | 17594C10233B0B710010AB9B /* APCalendarViewController.swift in Sources */, 341 | ); 342 | runOnlyForDeploymentPostprocessing = 0; 343 | }; 344 | 173925C1231303F400EFC5C3 /* Sources */ = { 345 | isa = PBXSourcesBuildPhase; 346 | buildActionMask = 2147483647; 347 | files = ( 348 | 173925CA231303F400EFC5C3 /* AVCalendarSampleTests.swift in Sources */, 349 | ); 350 | runOnlyForDeploymentPostprocessing = 0; 351 | }; 352 | 173925CC231303F400EFC5C3 /* Sources */ = { 353 | isa = PBXSourcesBuildPhase; 354 | buildActionMask = 2147483647; 355 | files = ( 356 | 173925D5231303F400EFC5C3 /* AVCalendarSampleUITests.swift in Sources */, 357 | ); 358 | runOnlyForDeploymentPostprocessing = 0; 359 | }; 360 | /* End PBXSourcesBuildPhase section */ 361 | 362 | /* Begin PBXTargetDependency section */ 363 | 173925C7231303F400EFC5C3 /* PBXTargetDependency */ = { 364 | isa = PBXTargetDependency; 365 | target = 173925B0231303F300EFC5C3 /* AVCalendarSample */; 366 | targetProxy = 173925C6231303F400EFC5C3 /* PBXContainerItemProxy */; 367 | }; 368 | 173925D2231303F400EFC5C3 /* PBXTargetDependency */ = { 369 | isa = PBXTargetDependency; 370 | target = 173925B0231303F300EFC5C3 /* AVCalendarSample */; 371 | targetProxy = 173925D1231303F400EFC5C3 /* PBXContainerItemProxy */; 372 | }; 373 | /* End PBXTargetDependency section */ 374 | 375 | /* Begin PBXVariantGroup section */ 376 | 173925B8231303F300EFC5C3 /* Main.storyboard */ = { 377 | isa = PBXVariantGroup; 378 | children = ( 379 | 173925B9231303F300EFC5C3 /* Base */, 380 | ); 381 | name = Main.storyboard; 382 | sourceTree = ""; 383 | }; 384 | 173925BD231303F400EFC5C3 /* LaunchScreen.storyboard */ = { 385 | isa = PBXVariantGroup; 386 | children = ( 387 | 173925BE231303F400EFC5C3 /* Base */, 388 | ); 389 | name = LaunchScreen.storyboard; 390 | sourceTree = ""; 391 | }; 392 | /* End PBXVariantGroup section */ 393 | 394 | /* Begin XCBuildConfiguration section */ 395 | 173925D7231303F400EFC5C3 /* Debug */ = { 396 | isa = XCBuildConfiguration; 397 | buildSettings = { 398 | ALWAYS_SEARCH_USER_PATHS = NO; 399 | CLANG_ANALYZER_NONNULL = YES; 400 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; 401 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; 402 | CLANG_CXX_LIBRARY = "libc++"; 403 | CLANG_ENABLE_MODULES = YES; 404 | CLANG_ENABLE_OBJC_ARC = YES; 405 | CLANG_ENABLE_OBJC_WEAK = YES; 406 | CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; 407 | CLANG_WARN_BOOL_CONVERSION = YES; 408 | CLANG_WARN_COMMA = YES; 409 | CLANG_WARN_CONSTANT_CONVERSION = YES; 410 | CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; 411 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 412 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES; 413 | CLANG_WARN_EMPTY_BODY = YES; 414 | CLANG_WARN_ENUM_CONVERSION = YES; 415 | CLANG_WARN_INFINITE_RECURSION = YES; 416 | CLANG_WARN_INT_CONVERSION = YES; 417 | CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; 418 | CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; 419 | CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; 420 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 421 | CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; 422 | CLANG_WARN_STRICT_PROTOTYPES = YES; 423 | CLANG_WARN_SUSPICIOUS_MOVE = YES; 424 | CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; 425 | CLANG_WARN_UNREACHABLE_CODE = YES; 426 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 427 | CODE_SIGN_IDENTITY = "iPhone Developer"; 428 | COPY_PHASE_STRIP = NO; 429 | DEBUG_INFORMATION_FORMAT = dwarf; 430 | ENABLE_STRICT_OBJC_MSGSEND = YES; 431 | ENABLE_TESTABILITY = YES; 432 | GCC_C_LANGUAGE_STANDARD = gnu11; 433 | GCC_DYNAMIC_NO_PIC = NO; 434 | GCC_NO_COMMON_BLOCKS = YES; 435 | GCC_OPTIMIZATION_LEVEL = 0; 436 | GCC_PREPROCESSOR_DEFINITIONS = ( 437 | "DEBUG=1", 438 | "$(inherited)", 439 | ); 440 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 441 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 442 | GCC_WARN_UNDECLARED_SELECTOR = YES; 443 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 444 | GCC_WARN_UNUSED_FUNCTION = YES; 445 | GCC_WARN_UNUSED_VARIABLE = YES; 446 | IPHONEOS_DEPLOYMENT_TARGET = 12.2; 447 | MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE; 448 | MTL_FAST_MATH = YES; 449 | ONLY_ACTIVE_ARCH = YES; 450 | SDKROOT = iphoneos; 451 | SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG; 452 | SWIFT_OPTIMIZATION_LEVEL = "-Onone"; 453 | }; 454 | name = Debug; 455 | }; 456 | 173925D8231303F400EFC5C3 /* Release */ = { 457 | isa = XCBuildConfiguration; 458 | buildSettings = { 459 | ALWAYS_SEARCH_USER_PATHS = NO; 460 | CLANG_ANALYZER_NONNULL = YES; 461 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; 462 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; 463 | CLANG_CXX_LIBRARY = "libc++"; 464 | CLANG_ENABLE_MODULES = YES; 465 | CLANG_ENABLE_OBJC_ARC = YES; 466 | CLANG_ENABLE_OBJC_WEAK = YES; 467 | CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; 468 | CLANG_WARN_BOOL_CONVERSION = YES; 469 | CLANG_WARN_COMMA = YES; 470 | CLANG_WARN_CONSTANT_CONVERSION = YES; 471 | CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; 472 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 473 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES; 474 | CLANG_WARN_EMPTY_BODY = YES; 475 | CLANG_WARN_ENUM_CONVERSION = YES; 476 | CLANG_WARN_INFINITE_RECURSION = YES; 477 | CLANG_WARN_INT_CONVERSION = YES; 478 | CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; 479 | CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; 480 | CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; 481 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 482 | CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; 483 | CLANG_WARN_STRICT_PROTOTYPES = YES; 484 | CLANG_WARN_SUSPICIOUS_MOVE = YES; 485 | CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; 486 | CLANG_WARN_UNREACHABLE_CODE = YES; 487 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 488 | CODE_SIGN_IDENTITY = "iPhone Developer"; 489 | COPY_PHASE_STRIP = NO; 490 | DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; 491 | ENABLE_NS_ASSERTIONS = NO; 492 | ENABLE_STRICT_OBJC_MSGSEND = YES; 493 | GCC_C_LANGUAGE_STANDARD = gnu11; 494 | GCC_NO_COMMON_BLOCKS = YES; 495 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 496 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 497 | GCC_WARN_UNDECLARED_SELECTOR = YES; 498 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 499 | GCC_WARN_UNUSED_FUNCTION = YES; 500 | GCC_WARN_UNUSED_VARIABLE = YES; 501 | IPHONEOS_DEPLOYMENT_TARGET = 12.2; 502 | MTL_ENABLE_DEBUG_INFO = NO; 503 | MTL_FAST_MATH = YES; 504 | SDKROOT = iphoneos; 505 | SWIFT_COMPILATION_MODE = wholemodule; 506 | SWIFT_OPTIMIZATION_LEVEL = "-O"; 507 | VALIDATE_PRODUCT = YES; 508 | }; 509 | name = Release; 510 | }; 511 | 173925DA231303F400EFC5C3 /* Debug */ = { 512 | isa = XCBuildConfiguration; 513 | buildSettings = { 514 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 515 | CODE_SIGN_STYLE = Manual; 516 | DEVELOPMENT_TEAM = ""; 517 | INFOPLIST_FILE = AVCalendarSample/Info.plist; 518 | LD_RUNPATH_SEARCH_PATHS = ( 519 | "$(inherited)", 520 | "@executable_path/Frameworks", 521 | ); 522 | PRODUCT_BUNDLE_IDENTIFIER = com.vyasanirudh.AVCalendarSample; 523 | PRODUCT_NAME = "$(TARGET_NAME)"; 524 | PROVISIONING_PROFILE_SPECIFIER = ""; 525 | SWIFT_VERSION = 5.0; 526 | TARGETED_DEVICE_FAMILY = "1,2"; 527 | }; 528 | name = Debug; 529 | }; 530 | 173925DB231303F400EFC5C3 /* Release */ = { 531 | isa = XCBuildConfiguration; 532 | buildSettings = { 533 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 534 | CODE_SIGN_STYLE = Manual; 535 | DEVELOPMENT_TEAM = ""; 536 | INFOPLIST_FILE = AVCalendarSample/Info.plist; 537 | LD_RUNPATH_SEARCH_PATHS = ( 538 | "$(inherited)", 539 | "@executable_path/Frameworks", 540 | ); 541 | PRODUCT_BUNDLE_IDENTIFIER = com.vyasanirudh.AVCalendarSample; 542 | PRODUCT_NAME = "$(TARGET_NAME)"; 543 | PROVISIONING_PROFILE_SPECIFIER = ""; 544 | SWIFT_VERSION = 5.0; 545 | TARGETED_DEVICE_FAMILY = "1,2"; 546 | }; 547 | name = Release; 548 | }; 549 | 173925DD231303F400EFC5C3 /* Debug */ = { 550 | isa = XCBuildConfiguration; 551 | buildSettings = { 552 | ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = YES; 553 | BUNDLE_LOADER = "$(TEST_HOST)"; 554 | CODE_SIGN_STYLE = Automatic; 555 | INFOPLIST_FILE = AVCalendarSampleTests/Info.plist; 556 | LD_RUNPATH_SEARCH_PATHS = ( 557 | "$(inherited)", 558 | "@executable_path/Frameworks", 559 | "@loader_path/Frameworks", 560 | ); 561 | PRODUCT_BUNDLE_IDENTIFIER = com.vyasanirudh.AVCalendarSampleTests; 562 | PRODUCT_NAME = "$(TARGET_NAME)"; 563 | SWIFT_VERSION = 5.0; 564 | TARGETED_DEVICE_FAMILY = "1,2"; 565 | TEST_HOST = "$(BUILT_PRODUCTS_DIR)/AVCalendarSample.app/AVCalendarSample"; 566 | }; 567 | name = Debug; 568 | }; 569 | 173925DE231303F400EFC5C3 /* Release */ = { 570 | isa = XCBuildConfiguration; 571 | buildSettings = { 572 | ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = YES; 573 | BUNDLE_LOADER = "$(TEST_HOST)"; 574 | CODE_SIGN_STYLE = Automatic; 575 | INFOPLIST_FILE = AVCalendarSampleTests/Info.plist; 576 | LD_RUNPATH_SEARCH_PATHS = ( 577 | "$(inherited)", 578 | "@executable_path/Frameworks", 579 | "@loader_path/Frameworks", 580 | ); 581 | PRODUCT_BUNDLE_IDENTIFIER = com.vyasanirudh.AVCalendarSampleTests; 582 | PRODUCT_NAME = "$(TARGET_NAME)"; 583 | SWIFT_VERSION = 5.0; 584 | TARGETED_DEVICE_FAMILY = "1,2"; 585 | TEST_HOST = "$(BUILT_PRODUCTS_DIR)/AVCalendarSample.app/AVCalendarSample"; 586 | }; 587 | name = Release; 588 | }; 589 | 173925E0231303F400EFC5C3 /* Debug */ = { 590 | isa = XCBuildConfiguration; 591 | buildSettings = { 592 | ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = YES; 593 | CODE_SIGN_STYLE = Automatic; 594 | INFOPLIST_FILE = AVCalendarSampleUITests/Info.plist; 595 | LD_RUNPATH_SEARCH_PATHS = ( 596 | "$(inherited)", 597 | "@executable_path/Frameworks", 598 | "@loader_path/Frameworks", 599 | ); 600 | PRODUCT_BUNDLE_IDENTIFIER = com.vyasanirudh.AVCalendarSampleUITests; 601 | PRODUCT_NAME = "$(TARGET_NAME)"; 602 | SWIFT_VERSION = 5.0; 603 | TARGETED_DEVICE_FAMILY = "1,2"; 604 | TEST_TARGET_NAME = AVCalendarSample; 605 | }; 606 | name = Debug; 607 | }; 608 | 173925E1231303F400EFC5C3 /* Release */ = { 609 | isa = XCBuildConfiguration; 610 | buildSettings = { 611 | ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = YES; 612 | CODE_SIGN_STYLE = Automatic; 613 | INFOPLIST_FILE = AVCalendarSampleUITests/Info.plist; 614 | LD_RUNPATH_SEARCH_PATHS = ( 615 | "$(inherited)", 616 | "@executable_path/Frameworks", 617 | "@loader_path/Frameworks", 618 | ); 619 | PRODUCT_BUNDLE_IDENTIFIER = com.vyasanirudh.AVCalendarSampleUITests; 620 | PRODUCT_NAME = "$(TARGET_NAME)"; 621 | SWIFT_VERSION = 5.0; 622 | TARGETED_DEVICE_FAMILY = "1,2"; 623 | TEST_TARGET_NAME = AVCalendarSample; 624 | }; 625 | name = Release; 626 | }; 627 | /* End XCBuildConfiguration section */ 628 | 629 | /* Begin XCConfigurationList section */ 630 | 173925AC231303F300EFC5C3 /* Build configuration list for PBXProject "AVCalendarSample" */ = { 631 | isa = XCConfigurationList; 632 | buildConfigurations = ( 633 | 173925D7231303F400EFC5C3 /* Debug */, 634 | 173925D8231303F400EFC5C3 /* Release */, 635 | ); 636 | defaultConfigurationIsVisible = 0; 637 | defaultConfigurationName = Release; 638 | }; 639 | 173925D9231303F400EFC5C3 /* Build configuration list for PBXNativeTarget "AVCalendarSample" */ = { 640 | isa = XCConfigurationList; 641 | buildConfigurations = ( 642 | 173925DA231303F400EFC5C3 /* Debug */, 643 | 173925DB231303F400EFC5C3 /* Release */, 644 | ); 645 | defaultConfigurationIsVisible = 0; 646 | defaultConfigurationName = Release; 647 | }; 648 | 173925DC231303F400EFC5C3 /* Build configuration list for PBXNativeTarget "AVCalendarSampleTests" */ = { 649 | isa = XCConfigurationList; 650 | buildConfigurations = ( 651 | 173925DD231303F400EFC5C3 /* Debug */, 652 | 173925DE231303F400EFC5C3 /* Release */, 653 | ); 654 | defaultConfigurationIsVisible = 0; 655 | defaultConfigurationName = Release; 656 | }; 657 | 173925DF231303F400EFC5C3 /* Build configuration list for PBXNativeTarget "AVCalendarSampleUITests" */ = { 658 | isa = XCConfigurationList; 659 | buildConfigurations = ( 660 | 173925E0231303F400EFC5C3 /* Debug */, 661 | 173925E1231303F400EFC5C3 /* Release */, 662 | ); 663 | defaultConfigurationIsVisible = 0; 664 | defaultConfigurationName = Release; 665 | }; 666 | /* End XCConfigurationList section */ 667 | }; 668 | rootObject = 173925A9231303F300EFC5C3 /* Project object */; 669 | } 670 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendarSample.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | IDEDidComputeMac32BitWarning 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendarSample.xcodeproj/project.xcworkspace/xcuserdata/anirudh-personal.xcuserdatad/UserInterfaceState.xcuserstate: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendarSample.xcodeproj/project.xcworkspace/xcuserdata/anirudh-personal.xcuserdatad/UserInterfaceState.xcuserstate -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendarSample.xcodeproj/xcuserdata/anirudh-personal.xcuserdatad/xcschemes/xcschememanagement.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | SchemeUserState 6 | 7 | AVCalendarSample.xcscheme_^#shared#^_ 8 | 9 | orderHint 10 | 2 11 | 12 | 13 | 14 | 15 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendarSample/AppDelegate.swift: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.swift 3 | // AVCalendarSample 4 | // 5 | // Created by Anirudh on 25/08/19. 6 | // Copyright © 2019 Anirudh Vyas. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | @UIApplicationMain 12 | class AppDelegate: UIResponder, UIApplicationDelegate { 13 | 14 | var window: UIWindow? 15 | 16 | 17 | func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool { 18 | // Override point for customization after application launch. 19 | return true 20 | } 21 | 22 | func applicationWillResignActive(_ application: UIApplication) { 23 | // Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state. 24 | // Use this method to pause ongoing tasks, disable timers, and invalidate graphics rendering callbacks. Games should use this method to pause the game. 25 | } 26 | 27 | func applicationDidEnterBackground(_ application: UIApplication) { 28 | // Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later. 29 | // If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits. 30 | } 31 | 32 | func applicationWillEnterForeground(_ application: UIApplication) { 33 | // Called as part of the transition from the background to the active state; here you can undo many of the changes made on entering the background. 34 | } 35 | 36 | func applicationDidBecomeActive(_ application: UIApplication) { 37 | // Restart any tasks that were paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface. 38 | } 39 | 40 | func applicationWillTerminate(_ application: UIApplication) { 41 | // Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:. 42 | } 43 | 44 | 45 | } 46 | 47 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendarSample/Assets.xcassets/AppIcon.appiconset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "iphone", 5 | "size" : "20x20", 6 | "scale" : "2x" 7 | }, 8 | { 9 | "idiom" : "iphone", 10 | "size" : "20x20", 11 | "scale" : "3x" 12 | }, 13 | { 14 | "idiom" : "iphone", 15 | "size" : "29x29", 16 | "scale" : "2x" 17 | }, 18 | { 19 | "idiom" : "iphone", 20 | "size" : "29x29", 21 | "scale" : "3x" 22 | }, 23 | { 24 | "idiom" : "iphone", 25 | "size" : "40x40", 26 | "scale" : "2x" 27 | }, 28 | { 29 | "idiom" : "iphone", 30 | "size" : "40x40", 31 | "scale" : "3x" 32 | }, 33 | { 34 | "idiom" : "iphone", 35 | "size" : "60x60", 36 | "scale" : "2x" 37 | }, 38 | { 39 | "idiom" : "iphone", 40 | "size" : "60x60", 41 | "scale" : "3x" 42 | }, 43 | { 44 | "idiom" : "ipad", 45 | "size" : "20x20", 46 | "scale" : "1x" 47 | }, 48 | { 49 | "idiom" : "ipad", 50 | "size" : "20x20", 51 | "scale" : "2x" 52 | }, 53 | { 54 | "idiom" : "ipad", 55 | "size" : "29x29", 56 | "scale" : "1x" 57 | }, 58 | { 59 | "idiom" : "ipad", 60 | "size" : "29x29", 61 | "scale" : "2x" 62 | }, 63 | { 64 | "idiom" : "ipad", 65 | "size" : "40x40", 66 | "scale" : "1x" 67 | }, 68 | { 69 | "idiom" : "ipad", 70 | "size" : "40x40", 71 | "scale" : "2x" 72 | }, 73 | { 74 | "idiom" : "ipad", 75 | "size" : "76x76", 76 | "scale" : "1x" 77 | }, 78 | { 79 | "idiom" : "ipad", 80 | "size" : "76x76", 81 | "scale" : "2x" 82 | }, 83 | { 84 | "idiom" : "ipad", 85 | "size" : "83.5x83.5", 86 | "scale" : "2x" 87 | }, 88 | { 89 | "idiom" : "ios-marketing", 90 | "size" : "1024x1024", 91 | "scale" : "1x" 92 | } 93 | ], 94 | "info" : { 95 | "version" : 1, 96 | "author" : "xcode" 97 | } 98 | } -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendarSample/Assets.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendarSample/Base.lproj/LaunchScreen.storyboard: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendarSample/Base.lproj/Main.storyboard: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendarSample/Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | $(DEVELOPMENT_LANGUAGE) 7 | CFBundleExecutable 8 | $(EXECUTABLE_NAME) 9 | CFBundleIdentifier 10 | $(PRODUCT_BUNDLE_IDENTIFIER) 11 | CFBundleInfoDictionaryVersion 12 | 6.0 13 | CFBundleName 14 | $(PRODUCT_NAME) 15 | CFBundlePackageType 16 | APPL 17 | CFBundleShortVersionString 18 | 1.0 19 | CFBundleVersion 20 | 1 21 | LSRequiresIPhoneOS 22 | 23 | UILaunchStoryboardName 24 | LaunchScreen 25 | UIMainStoryboardFile 26 | Main 27 | UIRequiredDeviceCapabilities 28 | 29 | armv7 30 | 31 | UISupportedInterfaceOrientations 32 | 33 | UIInterfaceOrientationPortrait 34 | UIInterfaceOrientationLandscapeLeft 35 | UIInterfaceOrientationLandscapeRight 36 | 37 | UISupportedInterfaceOrientations~ipad 38 | 39 | UIInterfaceOrientationPortrait 40 | UIInterfaceOrientationPortraitUpsideDown 41 | UIInterfaceOrientationLandscapeLeft 42 | UIInterfaceOrientationLandscapeRight 43 | 44 | 45 | 46 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendarSample/Screenshot.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vyasanirudh/AVCalendar/2faa3fdca773244984b69cefde11a7e15b26ea61/AVCalendarSample/AVCalendarSample/Screenshot.png -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendarSample/ViewController.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.swift 3 | // SampleCalendarView 4 | // 5 | // Created by Anirudh on 21/07/19. 6 | // Copyright © 2019 Anirudh Vyas. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | class ViewController: UIViewController { 12 | 13 | @IBOutlet weak var selectDateButton: UIButton! 14 | private let calendar: AVCalendarViewController = AVCalendarViewController.calendar 15 | private var selectedDate: AVDate? 16 | override func viewDidLoad() { 17 | super.viewDidLoad() 18 | // Do any additional setup after loading the view. 19 | } 20 | 21 | override func viewDidAppear(_ animated: Bool) { 22 | super.viewDidAppear(animated) 23 | } 24 | 25 | private func showTheCalendar() { 26 | calendar.dateStyleComponents = CalendarComponentStyle(backgroundColor: UIColor(red: 89/255, green: 65/255, blue: 102/255, alpha: 1.0), 27 | textColor: .white, 28 | highlightColor: UIColor(red: 126/255, green: 192/255, blue: 196/255, alpha: 1.0).withAlphaComponent(0.5)) 29 | calendar.yearStyleComponents = CalendarComponentStyle(backgroundColor: UIColor(red: 126/255, green: 192/255, blue: 196/255, alpha: 1.0), 30 | textColor: .black, highlightColor: .white) 31 | calendar.monthStyleComponents = CalendarComponentStyle(backgroundColor: UIColor(red: 47/255, green: 60/255, blue: 95/255, alpha: 1.0), 32 | textColor: UIColor(red: 126/255, green: 192/255, blue: 196/255, alpha: 1.0), 33 | highlightColor: UIColor.white) 34 | calendar.subscriber = { [weak self] (date) in guard let checkedSelf = self else { return } 35 | if date != nil { 36 | checkedSelf.selectedDate = date 37 | let _ = Date(timeIntervalSince1970: TimeInterval(date?.doubleVal ?? 0)) 38 | if let day = date?.day, let month = date?.month, let year = date?.year { 39 | let dateString = day + " " + month + " " + year 40 | checkedSelf.selectDateButton.setTitle(dateString, for: .normal) 41 | } 42 | } 43 | } 44 | calendar.preSelectedDate = selectedDate 45 | self.present(calendar, animated: false, completion: nil) 46 | } 47 | 48 | 49 | @IBAction func buttonAction(_ sender: UIButton) { 50 | showTheCalendar() 51 | } 52 | } 53 | 54 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendarSampleTests/AVCalendarSampleTests.swift: -------------------------------------------------------------------------------- 1 | // 2 | // AVCalendarSampleTests.swift 3 | // AVCalendarSampleTests 4 | // 5 | // Created by Anirudh on 25/08/19. 6 | // Copyright © 2019 Anirudh Vyas. All rights reserved. 7 | // 8 | 9 | import XCTest 10 | @testable import AVCalendarSample 11 | 12 | class AVCalendarSampleTests: XCTestCase { 13 | 14 | override func setUp() { 15 | // Put setup code here. This method is called before the invocation of each test method in the class. 16 | } 17 | 18 | override func tearDown() { 19 | // Put teardown code here. This method is called after the invocation of each test method in the class. 20 | } 21 | 22 | func testExample() { 23 | // This is an example of a functional test case. 24 | // Use XCTAssert and related functions to verify your tests produce the correct results. 25 | } 26 | 27 | func testPerformanceExample() { 28 | // This is an example of a performance test case. 29 | self.measure { 30 | // Put the code you want to measure the time of here. 31 | } 32 | } 33 | 34 | } 35 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendarSampleTests/Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | $(DEVELOPMENT_LANGUAGE) 7 | CFBundleExecutable 8 | $(EXECUTABLE_NAME) 9 | CFBundleIdentifier 10 | $(PRODUCT_BUNDLE_IDENTIFIER) 11 | CFBundleInfoDictionaryVersion 12 | 6.0 13 | CFBundleName 14 | $(PRODUCT_NAME) 15 | CFBundlePackageType 16 | BNDL 17 | CFBundleShortVersionString 18 | 1.0 19 | CFBundleVersion 20 | 1 21 | 22 | 23 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendarSampleUITests/AVCalendarSampleUITests.swift: -------------------------------------------------------------------------------- 1 | // 2 | // AVCalendarSampleUITests.swift 3 | // AVCalendarSampleUITests 4 | // 5 | // Created by Anirudh on 25/08/19. 6 | // Copyright © 2019 Anirudh Vyas. All rights reserved. 7 | // 8 | 9 | import XCTest 10 | 11 | class AVCalendarSampleUITests: XCTestCase { 12 | 13 | override func setUp() { 14 | // Put setup code here. This method is called before the invocation of each test method in the class. 15 | 16 | // In UI tests it is usually best to stop immediately when a failure occurs. 17 | continueAfterFailure = false 18 | 19 | // UI tests must launch the application that they test. Doing this in setup will make sure it happens for each test method. 20 | XCUIApplication().launch() 21 | 22 | // In UI tests it’s important to set the initial state - such as interface orientation - required for your tests before they run. The setUp method is a good place to do this. 23 | } 24 | 25 | override func tearDown() { 26 | // Put teardown code here. This method is called after the invocation of each test method in the class. 27 | } 28 | 29 | func testExample() { 30 | // Use recording to get started writing UI tests. 31 | // Use XCTAssert and related functions to verify your tests produce the correct results. 32 | } 33 | 34 | } 35 | -------------------------------------------------------------------------------- /AVCalendarSample/AVCalendarSampleUITests/Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | $(DEVELOPMENT_LANGUAGE) 7 | CFBundleExecutable 8 | $(EXECUTABLE_NAME) 9 | CFBundleIdentifier 10 | $(PRODUCT_BUNDLE_IDENTIFIER) 11 | CFBundleInfoDictionaryVersion 12 | 6.0 13 | CFBundleName 14 | $(PRODUCT_NAME) 15 | CFBundlePackageType 16 | BNDL 17 | CFBundleShortVersionString 18 | 1.0 19 | CFBundleVersion 20 | 1 21 | 22 | 23 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2019 vyasanirudh 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # AVCalendar ![License MIT](https://go-shields.herokuapp.com/license-MIT-blue.png) 2 | A sample AVCalendar app. 3 | 4 | --- 5 | # Adding AVCalendar 6 | 7 | Just add the required files to your project space and you're done! 8 | 9 | --- 10 | 11 | # Usage 12 | 13 | A sample project has been added to explain the fairly simple usage process. 14 | 15 | --- 16 | # Preview 17 | 18 | ![alt text](https://raw.githubusercontent.com/vyasanirudh/AVCalendar/master/AVCalendarSample/AVCalendarSample/Screenshot.png) 19 | 20 | --- 21 | 22 | # Development 23 | 24 | * [Anirudh Vyas](https://github.com/vyasanirudh) 25 | 26 | --- 27 | 28 | # Feedback 29 | I'd love to hear the feedback. Create Github issues, or hit me up on http://www.dextraltech.com 30 | 31 | --- 32 | 33 | # License 34 | `AVCalendarFramework` is available under the MIT license. See the LICENSE file for more info. 35 | --------------------------------------------------------------------------------