Просмотр исходного кода

added a date picker class, implemented the date picker class for tvOS instances, tried to get the web view working properly on tvOS but it wouldn't cooperate

Kevin Bradley лет назад: 5
Родитель
Сommit
1a7884005a

+ 2 - 2
Classes/Editing/ArgumentInputViews/FLEXArgumentInputDateView.m

@@ -14,7 +14,7 @@
 @interface FLEXArgumentInputDateView ()
 
 #if TARGET_OS_TV
-@property (nonatomic) UIFakeDatePicker *datePicker;
+@property (nonatomic) KBDatePickerView *datePicker;
 #else
 @property (nonatomic) UIDatePicker *datePicker;
 #endif
@@ -33,7 +33,7 @@
         self.datePicker.calendar = [NSCalendar calendarWithIdentifier:NSCalendarIdentifierGregorian];
         self.datePicker.timeZone = [NSTimeZone timeZoneWithAbbreviation:@"UTC"];
 #else
-        self.datePicker = [UIFakeDatePicker new];
+        self.datePicker = [[KBDatePickerView alloc] init];
 #endif
         
         [self addSubview:self.datePicker];

+ 8 - 1
Classes/Editing/FLEXFieldEditorViewController.m

@@ -15,6 +15,7 @@
 #import "FLEXColor.h"
 #import "UIBarButtonItem+FLEX.h"
 #import <TargetConditionals.h>
+#import "FLEXArgumentInputDateView.h"
 
 @interface FLEXFieldEditorViewController () <FLEXArgumentInputViewDelegate>
 
@@ -83,7 +84,6 @@
     inputView.inputValue = self.currentValue;
     inputView.delegate = self;
     self.fieldEditorView.argumentInputViews = @[inputView];
-
     // Don't show a "set" button for switches; we mutate when the switch is flipped
     if ([inputView isKindOfClass:[FLEXArgumentInputSwitchView class]]) {
         self.actionButton.enabled = NO;
@@ -140,6 +140,13 @@
 - (void)viewWillLayoutSubviews {
     [super viewWillLayoutSubviews];
 #if TARGET_OS_TV
+    
+    FLEXArgumentInputView *inputView = [FLEXArgumentInputViewFactory argumentInputViewForTypeEncoding:self.typeEncoding];
+    if ([inputView isKindOfClass:[FLEXArgumentInputDateView class]]){
+        [self actionButton].frame = CGRectMake(100, 400, 200, 60);
+        return;
+    }
+    
     CGRect getterFrame = _getterButton.frame;
     CGFloat actionOffset = [[self actionButton] frame].origin.y;
     //CGRect fieldEditorFrame = self.fieldEditorView.frame;

+ 5 - 2
Classes/Editing/FLEXVariableEditorViewController.m

@@ -16,6 +16,7 @@
 #import "FLEXArgumentInputViewFactory.h"
 #import "FLEXObjectExplorerViewController.h"
 #import "UIBarButtonItem+FLEX.h"
+#import "FLEXArgumentInputDateView.h"
 
 @interface FLEXVariableEditorViewController () <UIScrollViewDelegate>
 @property (nonatomic) UIScrollView *scrollView;
@@ -56,7 +57,6 @@
 
 - (void)keyboardDidShow:(NSNotification *)notification {
     
-    NSLog(@"[FLEXLog] keyboardDidShow!");
     CGRect keyboardRectInWindow = [[[notification userInfo] objectForKey:UIKeyboardFrameEndUserInfoKey] CGRectValue];
     CGSize keyboardSize = [self.view convertRect:keyboardRectInWindow fromView:nil].size;
     UIEdgeInsets scrollInsets = self.scrollView.contentInset;
@@ -75,7 +75,7 @@
 }
 
 - (void)keyboardWillHide:(NSNotification *)notification {
-    NSLog(@"[FLEXLog] keyboardWillHide!");
+
     UIEdgeInsets scrollInsets = self.scrollView.contentInset;
     scrollInsets.bottom = 0.0;
     self.scrollView.contentInset = scrollInsets;
@@ -120,12 +120,15 @@
     CGSize fieldEditorSize = [self.fieldEditorView sizeThatFits:constrainSize];
     self.fieldEditorView.frame = CGRectMake(0, 0, fieldEditorSize.width, fieldEditorSize.height);
 #if TARGET_OS_TV
+    
     CGRect actionFrame = _actionButton.frame;
     CGRect fieldEditorFrame = self.fieldEditorView.frame;
     CGFloat buttonOffset = (fieldEditorFrame.origin.y + fieldEditorFrame.size.height) + (130 + 67);
     actionFrame.origin.y = buttonOffset;
     _actionButton.frame = actionFrame;
     
+    
+    
 #endif
     self.scrollView.contentSize = fieldEditorSize;
 }

+ 47 - 4
Classes/GlobalStateExplorers/FLEXWebViewController.m

@@ -9,10 +9,15 @@
 #import "FLEXWebViewController.h"
 #import "FLEXUtility.h"
 #import <WebKit/WebKit.h>
+#import <TargetConditionals.h>
 
 @interface FLEXWebViewController () <WKNavigationDelegate>
 
+#if !TARGET_OS_TV
 @property (nonatomic) WKWebView *webView;
+#else
+@property (nonatomic) UIWebView *webView;
+#endif
 @property (nonatomic) NSString *originalText;
 
 @end
@@ -22,14 +27,20 @@
 - (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil {
     self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
     if (self) {
+        
+#if !TARGET_OS_TV
         WKWebViewConfiguration *configuration = [WKWebViewConfiguration new];
-
+        
         if (@available(iOS 10.0, *)) {
             configuration.dataDetectorTypes = UIDataDetectorTypeLink;
         }
-
+        
         self.webView = [[WKWebView alloc] initWithFrame:CGRectZero configuration:configuration];
         self.webView.navigationDelegate = self;
+#else
+        self.webView = [[UIWebView alloc] initWithFrame:CGRectZero];
+        self.webView.delegate = self;
+#endif
     }
     return self;
 }
@@ -55,9 +66,15 @@
 
 - (void)dealloc {
     // WKWebView's delegate is assigned so we need to clear it manually.
+#if !TARGET_OS_TV
     if (_webView.navigationDelegate == self) {
         _webView.navigationDelegate = nil;
     }
+#else
+    if (_webView.delegate = self){
+        _webView.delegate = nil;
+    }
+#endif
 }
 
 - (void)viewDidLoad {
@@ -73,11 +90,37 @@
 }
 
 - (void)copyButtonTapped:(id)sender {
-    #if !TARGET_OS_TV
+#if !TARGET_OS_TV
     [UIPasteboard.generalPasteboard setString:self.originalText];
-    #endif
+#endif
+}
+
+#pragma mark - UIWebView Delegate
+
+-(void) webViewDidStartLoad:(UIWebView *)webView {
+    LOG_SELF;
 }
 
+- (BOOL)webView:(UIWebView *)webView shouldStartLoadWithRequest:(NSURLRequest *)request navigationType:(UIWebViewNavigationType)navigationType {
+    FXLog(@"navtype: %lu", navigationType);
+    FXLog(@"urL: %@", request.URL);
+    FXLog(@"scheme: %@", request.URL.scheme);
+    FXLog(@"navigationType: %lu", navigationType);
+    if (navigationType == UIWebViewNavigationTypeOther){
+        return YES;
+    } else {
+        FLEXWebViewController *webVC = [[[self class] alloc] initWithURL:[request URL]];
+        webVC.title = [[request URL] absoluteString];
+        [self.navigationController pushViewController:webVC animated:YES];
+        return NO;//? maybe?
+    }
+    return YES;
+}
+
+-(void) webViewDidFinishLoad:(UIWebView *)webView {
+    LOG_SELF;
+    
+}
 
 #pragma mark - WKWebView Delegate
 

+ 6 - 2
Classes/GlobalStateExplorers/FileBrowser/FLEXFileBrowserController.m

@@ -471,11 +471,15 @@ typedef NS_ENUM(NSUInteger, FLEXFileBrowserSortAttribute) {
 }
 
 - (void)fileBrowserShare:(UITableViewCell *)sender {
-#if !TARGET_OS_TV
     NSIndexPath *indexPath = [self.tableView indexPathForCell:sender];
     NSString *pathString = [self filePathAtIndexPath:indexPath];
     NSURL *filePath = [NSURL fileURLWithPath:pathString];
-
+#if TARGET_OS_TV
+    //This only helps on jailbroken AppleTV - it will allow you to share the files over AirDrop, no share option exists otherwise.
+    NSURL *url = [NSURL URLWithString:[NSString stringWithFormat:@"airdropper://%@", pathString]];
+    UIApplication *application = [UIApplication sharedApplication];
+    [application openURL:url options:@{} completionHandler:nil];
+#else
     BOOL isDirectory = NO;
     [NSFileManager.defaultManager fileExistsAtPath:pathString isDirectory:&isDirectory];
 

+ 8 - 0
FLEX.xcodeproj/project.pbxproj

@@ -26,6 +26,8 @@
 		325D7AE825955C3500CC6B10 /* FLEXFontListTableViewController.h in Headers */ = {isa = PBXBuildFile; fileRef = 325D7AE625955C3500CC6B10 /* FLEXFontListTableViewController.h */; };
 		325D7B11259763BD00CC6B10 /* KBSlider.h in Headers */ = {isa = PBXBuildFile; fileRef = 325D7B0F259763BD00CC6B10 /* KBSlider.h */; };
 		325D7B12259763BD00CC6B10 /* KBSlider.m in Sources */ = {isa = PBXBuildFile; fileRef = 325D7B10259763BD00CC6B10 /* KBSlider.m */; };
+		325D7B3E2597BA2800CC6B10 /* KBDatePickerView.h in Headers */ = {isa = PBXBuildFile; fileRef = 325D7B3C2597BA2700CC6B10 /* KBDatePickerView.h */; };
+		325D7B3F2597BA2800CC6B10 /* KBDatePickerView.m in Sources */ = {isa = PBXBuildFile; fileRef = 325D7B3D2597BA2800CC6B10 /* KBDatePickerView.m */; };
 		32D4E15B259273E60027F238 /* fakes.h in Headers */ = {isa = PBXBuildFile; fileRef = 32D4E15A259273E60027F238 /* fakes.h */; };
 		32D4E15D2592749D0027F238 /* fakes.m in Sources */ = {isa = PBXBuildFile; fileRef = 32D4E15C2592749D0027F238 /* fakes.m */; };
 		3A4C94251B5B20570088C3F2 /* FLEX.h in Headers */ = {isa = PBXBuildFile; fileRef = 3A4C94241B5B20570088C3F2 /* FLEX.h */; settings = {ATTRIBUTES = (Public, ); }; };
@@ -393,6 +395,8 @@
 		325D7B0E25973F2E00CC6B10 /* postScript.sh */ = {isa = PBXFileReference; lastKnownFileType = text.script.sh; path = postScript.sh; sourceTree = SOURCE_ROOT; };
 		325D7B0F259763BD00CC6B10 /* KBSlider.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = KBSlider.h; sourceTree = "<group>"; };
 		325D7B10259763BD00CC6B10 /* KBSlider.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = KBSlider.m; sourceTree = "<group>"; };
+		325D7B3C2597BA2700CC6B10 /* KBDatePickerView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = KBDatePickerView.h; sourceTree = "<group>"; };
+		325D7B3D2597BA2800CC6B10 /* KBDatePickerView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = KBDatePickerView.m; sourceTree = "<group>"; };
 		32D4E15A259273E60027F238 /* fakes.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = fakes.h; sourceTree = "<group>"; };
 		32D4E15C2592749D0027F238 /* fakes.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = fakes.m; sourceTree = "<group>"; };
 		3A4C941F1B5B20570088C3F2 /* FLEX.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = FLEX.framework; sourceTree = BUILT_PRODUCTS_DIR; };
@@ -777,6 +781,8 @@
 				325D7AE125953F8E00CC6B10 /* KBSelectableTextView.m */,
 				325D7B0F259763BD00CC6B10 /* KBSlider.h */,
 				325D7B10259763BD00CC6B10 /* KBSlider.m */,
+				325D7B3C2597BA2700CC6B10 /* KBDatePickerView.h */,
+				325D7B3D2597BA2800CC6B10 /* KBDatePickerView.m */,
 			);
 			path = tvOS;
 			sourceTree = "<group>";
@@ -1627,6 +1633,7 @@
 				71E1C2152307FBB800F5032A /* FLEXKeychainQuery.h in Headers */,
 				C36B096523E0D4A1008F5D47 /* UIMenu+FLEX.h in Headers */,
 				C36FBFD6230F3B98008D95D5 /* FLEXIvar.h in Headers */,
+				325D7B3E2597BA2800CC6B10 /* KBDatePickerView.h in Headers */,
 				C3A9423823C51B8D006871A3 /* FHSRangeSlider.h in Headers */,
 				C398626123AD70DF007E6793 /* FLEXKeyboardToolbar.h in Headers */,
 				C386D6F2241A96AD00699085 /* FLEXMacros.h in Headers */,
@@ -1810,6 +1817,7 @@
 				C398624E23AD6C67007E6793 /* FLEXRuntimeKeyPath.m in Sources */,
 				C3694DC323EA147F006625D7 /* UIBarButtonItem+FLEX.m in Sources */,
 				C36FBFD4230F3B98008D95D5 /* FLEXProtocol.m in Sources */,
+				325D7B3F2597BA2800CC6B10 /* KBDatePickerView.m in Sources */,
 				C34D4EB123A2ABD900C1F903 /* FLEXLayerShortcuts.m in Sources */,
 				C38F3F32230C958F004E3731 /* FLEXAlert.m in Sources */,
 				C301994B2409B38A00759E8E /* CALayer+FLEX.m in Sources */,

BIN
layout/Library/Frameworks/FLEX.framework/FLEX


+ 1 - 1
tvOS/FLEXFontListTableViewController.h

@@ -1,5 +1,5 @@
 #import <UIKit/UIKit.h>
 
 @interface FLEXFontListTableViewController : UITableViewController
-@property (nonatomic, copy, nullable) void (^itemSelectedBlock)(NSString *fontName);
+@property (nonatomic, copy, nullable) void (^itemSelectedBlock)(NSString * _Nullable fontName);
 @end

+ 6 - 0
tvOS/KBDatePickerView.h

@@ -0,0 +1,6 @@
+#import <UIKit/UIKit.h>
+
+@interface KBDatePickerView: UIView <UITableViewDelegate, UITableViewDataSource>
+@property NSDate * _Nonnull date;
+@property (nonatomic, copy, nullable) void (^itemSelectedBlock)(NSDate * _Nullable date);
+@end

+ 184 - 0
tvOS/KBDatePickerView.m

@@ -0,0 +1,184 @@
+#import "KBDatePickerView.h"
+
+@interface KBDatePickerView () {
+    NSDate *_currentDate;
+}
+
+@property UIStackView *datePickerStackView;
+@property UITableView *monthTable;
+@property UITableView *dayTable;
+@property UITableView *yearTable;
+@property UILabel *monthLabel;
+@property UILabel *dayLabel;
+@property UILabel *yearLabel;
+
+@end
+
+@implementation KBDatePickerView
+
+- (NSDate *)date {
+    if (!_currentDate){
+        [self setDate:[NSDate date]];
+    }
+    return _currentDate;
+}
+
+- (NSCalendar *)calendar {
+    return [NSCalendar currentCalendar];
+}
+
+- (void)setDate:(NSDate *)date {
+    _currentDate = date;
+    //_dateLabel.text = date.description;
+    [self scrollToCurrentDateAnimated:true];
+}
+
+
+- (id)init {
+    self = [super init];
+    if (![self date]){
+        [self setDate:[NSDate date]];
+    }
+    [self layoutViews];
+    return self;
+}
+
+- (void)scrollToCurrentDateAnimated:(BOOL)animated {
+    NSDateComponents *components = [[self calendar] components:NSCalendarUnitYear | NSCalendarUnitMonth | NSCalendarUnitDay fromDate:self.date];
+    [_monthTable selectRowAtIndexPath:[NSIndexPath indexPathForRow:components.month-1 inSection:0] animated:animated scrollPosition:UITableViewScrollPositionTop];
+    [_dayTable selectRowAtIndexPath:[NSIndexPath indexPathForRow:components.day-1 inSection:0] animated:animated scrollPosition:UITableViewScrollPositionTop];
+    [_yearTable selectRowAtIndexPath:[NSIndexPath indexPathForRow:1 inSection:0] animated:animated scrollPosition:UITableViewScrollPositionTop];
+}
+
+- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
+    if (tableView == _monthTable){
+        return [self calendar].monthSymbols.count;
+    } else if (tableView == _dayTable){
+        NSRange days = [[self calendar] rangeOfUnit:NSCalendarUnitDay inUnit:NSCalendarUnitMonth forDate:self.date];
+        return days.length;
+    } else {
+        return 3;
+    }
+}
+
+- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
+    
+    UITableViewCell *cell = nil;
+    if (tableView == _monthTable){
+        cell = [tableView dequeueReusableCellWithIdentifier:@"month"];
+        if (!cell){
+            cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:@"month"];
+        }
+        cell.textLabel.text = [[self calendar] monthSymbols][indexPath.row];
+        cell.textLabel.textAlignment = NSTextAlignmentCenter;
+    } else if (tableView == _dayTable){
+        cell = [tableView dequeueReusableCellWithIdentifier:@"day"];
+        if (!cell){
+            cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:@"day"];
+        }
+        cell.textLabel.text = [NSString stringWithFormat:@"%lu", indexPath.row + 1];
+        cell.textLabel.textAlignment = NSTextAlignmentCenter;
+    } else {
+        cell = [tableView dequeueReusableCellWithIdentifier:@"year"];
+        if (!cell){
+            cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:@"year"];
+        }
+        NSInteger year = [[self calendar] component:NSCalendarUnitYear fromDate:self.date];
+        cell.textLabel.text = [NSString stringWithFormat:@"%lu", year - 1 + indexPath.row];
+        cell.textLabel.textAlignment = NSTextAlignmentCenter;
+    }
+    return cell;
+}
+
+- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
+    
+    NSDateComponents *components = [[self calendar] components:NSCalendarUnitYear | NSCalendarUnitMonth | NSCalendarUnitDay fromDate:self.date];
+    if (tableView == _monthTable){
+        NSInteger month = indexPath.row + 1;
+        components.month = month;
+        NSDate *newDate = nil;
+        do {
+            newDate = [[self calendar] dateFromComponents:components];
+            components.day -= 1;
+        } while (newDate == nil || ([[self calendar] component:NSCalendarUnitMonth fromDate:newDate] != month));
+        [self setDate:newDate];
+        [[self dayTable] reloadData];
+        [[self yearTable] reloadData];
+    } else if (tableView == _dayTable){
+        components.day = indexPath.row + 1;
+        NSDate *newDate = [[self calendar] dateFromComponents:components];
+        if (newDate){
+            [self setDate:newDate];
+            [[self monthTable] reloadData];
+            [[self yearTable] reloadData];
+        }
+    } else {
+        NSInteger year = [[self calendar] component:NSCalendarUnitYear fromDate:self.date];
+        components.year = year - 1 + indexPath.row;
+        NSDate *newDate = nil;
+        do {
+            newDate = [[self calendar] dateFromComponents:components];
+            components.day -= 1;
+        } while (newDate == nil || ([[self calendar] component:NSCalendarUnitMonth fromDate:newDate] != components.month));
+        [self setDate:newDate];
+        [[self monthTable] reloadData];
+        [[self yearTable] reloadData];
+    }
+    if (self.itemSelectedBlock){
+        self.itemSelectedBlock(self.date);
+    }
+}
+
+- (CGSize)sizeThatFits:(CGSize)size {
+    CGSize sup = [super sizeThatFits:size];
+    return CGSizeMake(720, 128+81+60+40);
+}
+
+- (void)layoutViews {
+    
+    self.monthLabel = [[UILabel alloc] init];
+    self.monthLabel.translatesAutoresizingMaskIntoConstraints = false;
+    self.monthLabel.text = @"Month";
+    self.yearLabel = [[UILabel alloc] init];
+    self.yearLabel.translatesAutoresizingMaskIntoConstraints = false;
+    self.yearLabel.text = @"Year";
+    self.dayLabel = [[UILabel alloc] init];
+    self.dayLabel.translatesAutoresizingMaskIntoConstraints = false;
+    self.dayLabel.text = @"Day";
+
+    self.monthTable = [[UITableView alloc] initWithFrame:CGRectZero style:UITableViewStylePlain];
+    self.yearTable = [[UITableView alloc] initWithFrame:CGRectZero style:UITableViewStylePlain];
+    self.dayTable = [[UITableView alloc] initWithFrame:CGRectZero style:UITableViewStylePlain];
+    self.monthTable.delegate = self;
+    self.monthTable.dataSource = self;
+    self.yearTable.delegate = self;
+    self.yearTable.dataSource = self;
+    self.dayTable.delegate = self;
+    self.dayTable.dataSource = self;
+    
+    self.datePickerStackView = [[UIStackView alloc] initWithArrangedSubviews:@[self.monthTable, self.dayTable, self.yearTable]];
+    self.datePickerStackView.translatesAutoresizingMaskIntoConstraints = false;
+    self.datePickerStackView.spacing = 10;
+    self.datePickerStackView.axis = UILayoutConstraintAxisHorizontal;
+    self.datePickerStackView.alignment = UIStackViewAlignmentFill;
+    self.datePickerStackView.distribution = UIStackViewDistributionFillEqually;
+    [self.datePickerStackView.widthAnchor constraintEqualToConstant:720].active = true;
+    [self.datePickerStackView.heightAnchor constraintEqualToConstant:128].active = true;
+    
+    [self addSubview:self.datePickerStackView];
+    [self addSubview:self.monthLabel];
+    [self addSubview:self.yearLabel];
+    [self addSubview:self.dayLabel];
+
+    [self.datePickerStackView.centerXAnchor constraintEqualToAnchor:self.centerXAnchor].active = true;
+    [self.datePickerStackView.topAnchor constraintEqualToAnchor:self.dayLabel.bottomAnchor constant:60].active = true;
+    [self.monthLabel.topAnchor constraintEqualToAnchor:self.topAnchor constant:20].active = true;
+    [self.dayLabel.topAnchor constraintEqualToAnchor:self.topAnchor constant:20].active = true;
+    [self.dayLabel.centerXAnchor constraintEqualToAnchor:self.dayTable.centerXAnchor].active = true;
+    [self.monthLabel.centerXAnchor constraintEqualToAnchor:self.monthTable.centerXAnchor].active = true;
+    [self.yearLabel.centerXAnchor constraintEqualToAnchor:self.yearTable.centerXAnchor].active = true;
+    [self.yearLabel.topAnchor constraintEqualToAnchor:self.topAnchor constant:20].active = true;
+    [self.monthLabel.topAnchor constraintEqualToAnchor:self.topAnchor constant:20].active = true;
+}
+
+@end

+ 1 - 40
tvOS/fakes.h

@@ -9,46 +9,7 @@
 #import <UIKit/UIKit.h>
 #import "FLEXMacros.h"
 #import "KBSlider.h"
-
-typedef NS_ENUM(NSInteger, UIFakeDatePickerMode) {
-    UIFakeDatePickerModeTime,           // Displays hour, minute, and optionally AM/PM designation depending on the locale setting (e.g. 6 | 53 | PM)
-    UIFakeDatePickerModeDate,           // Displays month, day, and year depending on the locale setting (e.g. November | 15 | 2007)
-    UIFakeDatePickerModeDateAndTime,    // Displays date, hour, minute, and optionally AM/PM designation depending on the locale setting (e.g. Wed Nov 15 | 6 | 53 | PM)
-    UIFakeDatePickerModeCountDownTimer, // Displays hour and minute (e.g. 1 | 53)
-} ;
-
-typedef NS_ENUM(NSInteger, UIFakeDatePickerStyle) {
-    /// Automatically pick the best style available for the current platform & mode.
-    UIFakeDatePickerStyleAutomatic,
-    /// Use the wheels (UIPickerView) style.
-    UIFakeDatePickerStyleWheels,
-    /// Use a compact style for the date picker. Editing occurs in an overlay.
-    UIFakeDatePickerStyleCompact,
-};
-
-@interface UIFakeDatePicker : UIControl <NSCoding>
-@property (nonatomic) UIFakeDatePickerMode datePickerMode; // default is UIFakeDatePickerModeDateAndTime
-
-@property (nullable, nonatomic, strong) NSLocale   *locale;   // default is [NSLocale currentLocale]. setting nil returns to default
-@property (null_resettable, nonatomic, copy)   NSCalendar *calendar; // default is [NSCalendar currentCalendar]. setting nil returns to default
-@property (nullable, nonatomic, strong) NSTimeZone *timeZone; // default is nil. use current time zone or time zone from calendar
-
-@property (nonatomic, strong) NSDate * _Nonnull date;        // default is current dat _Nonnull e when picker created. Ignored in countdown timer mode. for that mode, picker starts at 0:00
-@property (nullable, nonatomic, strong) NSDate *minimumDate; // specify min/max date range. default is nil. When min > max, the values are ignored. Ignored in countdown timer mode
-@property (nullable, nonatomic, strong) NSDate *maximumDate; // default is nil
-
-@property (nonatomic) NSTimeInterval countDownDuration; // for UIFakeDatePickerModeCountDownTimer, ignored otherwise. default is 0.0. limit is 23:59 (86,399 seconds). value being set is div 60 (drops remaining seconds).
-@property (nonatomic) NSInteger      minuteInterval;    // display minutes wheel with interval. interval must be evenly divided into 60. default is 1. min is 1, max is 30
-
-- (void)setDate:(NSDate *_Nonnull)date animated:(BOOL)animated; // if a_Nonnullnimated is YES, animate the wheels of time to display the new date
-
-/// Request a style for the date picker. If the style changed, then the date picker may need to be resized and will generate a layout pass to display correctly.
-@property (nonatomic, readwrite, assign) UIFakeDatePickerStyle preferredDatePickerStyle;
-
-/// The style that the date picker is using for its layout. This property always returns a concrete style (never automatic).
-@property (nonatomic, readonly, assign) UIFakeDatePickerStyle datePickerStyle;
-
-@end
+#import "KBDatePickerView.h"
 
 @interface UIFakeSwitch : UIButton <NSCoding>
 @property(nullable, nonatomic, strong) UIColor *onTintColor;

+ 0 - 46
tvOS/fakes.m

@@ -8,52 +8,6 @@
 
 #import "fakes.h"
 
-@implementation UIFakeDatePicker
-
-- (void)setCalendar:(NSCalendar *)calendar {
-
-}
-
-- (void)setDate:(NSDate *_Nonnull)date animated:(BOOL)animated {
-    
-}
-
-- (NSCalendar *)calendar {
-    return [NSCalendar currentCalendar];
-}
-
-- (NSInteger) numberOfComponents {
-    return 0;
-}
-- (NSInteger)numberOfRowsInComponent:(NSInteger)component {
-    return 0;
-}
-- (CGSize)rowSizeForComponent:(NSInteger)component {
-    return CGSizeZero;
-}
-
-- (nullable UIView *)viewForRow:(NSInteger)row forComponent:(NSInteger)component {
-    return nil;
-}
-
-// Reloading whole view or single component
-- (void)reloadAllComponents {
-    
-}
-- (void)reloadComponent:(NSInteger)component {
-    
-}
-
-// selection. in this case, it means showing the appropriate row in the middle
-- (void)selectRow:(NSInteger)row inComponent:(NSInteger)component animated:(BOOL)animated {
-    
-}
-- (NSInteger)selectedRowInComponent:(NSInteger)component {
-    return -1;
-}
-
-@end
-
 @interface UIFakeSwitch() {
     BOOL _isOn;
 }