Files
peko-ios/YuMi/Modules/YMNewHome/View/CreateEventPickerContainerView.m

406 lines
15 KiB
Objective-C
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

#import "CreateEventPickerContainerView.h"
#import "EventConfigModel.h"
@interface CreateEventPickerContainerView () <UIGestureRecognizerDelegate, UIPickerViewDataSource, UIPickerViewDelegate>
@property (nonatomic, strong) EventConfigModel *configModel;
@property (nonatomic, strong) UIPickerView *pickerView;
@property (nonatomic, strong) NSDate *minDate;
@property (nonatomic, strong) NSDate *maxDate;
@property (nonatomic, strong) NSArray<NSDate *> *dateArray;
@property (nonatomic, strong) NSArray<NSString *> *monthArray;
@property (nonatomic, strong) NSArray<NSString *> *dayArray;
@property (nonatomic, strong) NSArray<NSString *> *hourArray;
@property (nonatomic, strong) NSDate *selectedDate;
// StartTime 相关
@property (nonatomic, strong) NSArray<NSDictionary *> *durationsOptions;
@end
@implementation CreateEventPickerContainerView {
UIView *_pickerBg;
UILabel *_titleLabel;
UIButton *_okButton;
}
- (instancetype)init {
self = [super init];
if (self) {
[self setupUI];
}
return self;
}
- (void)setupUI {
self.backgroundColor = [[UIColor blackColor] colorWithAlphaComponent:0.3];
// 底部白色背景
_pickerBg = [[UIView alloc] init];
_pickerBg.backgroundColor = [UIColor whiteColor];
_pickerBg.layer.cornerRadius = 16;
_pickerBg.clipsToBounds = YES;
[self addSubview:_pickerBg];
// 标题
_titleLabel = [[UILabel alloc] init];
_titleLabel.font = [UIFont systemFontOfSize:16 weight:UIFontWeightMedium];
_titleLabel.textColor = [UIColor blackColor];
_titleLabel.textAlignment = NSTextAlignmentCenter;
[_pickerBg addSubview:_titleLabel];
// OK 按钮
_okButton = [UIButton buttonWithType:UIButtonTypeSystem];
[_okButton setTitle:@"OK" forState:UIControlStateNormal];
[_okButton setTitleColor:UIColorFromRGB(0xff8c03) forState:UIControlStateNormal];
_okButton.titleLabel.font = [UIFont systemFontOfSize:16 weight:UIFontWeightMedium];
[_okButton addTarget:self action:@selector(okTapped) forControlEvents:UIControlEventTouchUpInside];
[_pickerBg addSubview:_okButton];
// Picker View
self.pickerView = [[UIPickerView alloc] init];
self.pickerView.dataSource = self;
self.pickerView.delegate = self;
[_pickerBg addSubview:self.pickerView];
// 点击背景关闭
UITapGestureRecognizer *tap = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(dismiss)];
[self addGestureRecognizer:tap];
tap.delegate = self;
// 布局
[_pickerBg mas_makeConstraints:^(MASConstraintMaker *make) {
make.left.right.bottom.equalTo(self);
make.height.mas_equalTo(320);
}];
[_titleLabel mas_makeConstraints:^(MASConstraintMaker *make) {
make.top.equalTo(_pickerBg).offset(8);
make.centerX.equalTo(_pickerBg);
}];
[_okButton mas_makeConstraints:^(MASConstraintMaker *make) {
make.centerY.equalTo(_titleLabel);
make.right.equalTo(_pickerBg).offset(-16);
}];
[self.pickerView mas_makeConstraints:^(MASConstraintMaker *make) {
make.top.equalTo(_titleLabel.mas_bottom).offset(8);
make.left.right.bottom.equalTo(_pickerBg);
}];
}
#pragma mark - UIGestureRecognizerDelegate
- (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldReceiveTouch:(UITouch *)touch {
if ([touch.view isDescendantOfView:_pickerBg]) {
return NO;
}
return YES;
}
#pragma mark - Public Methods
- (NSDictionary *)formatTimeWithString:(NSString *)minutesString {
// 将字符串转换为整数
NSInteger minutes = [minutesString integerValue];
NSMutableDictionary *result = [NSMutableDictionary dictionary];
if (minutes < 60) {
// 小于60分钟直接显示分钟
result[@"title"] = [NSString stringWithFormat:@"%@分钟", minutesString];
result[@"minutes"] = minutesString;
} else if (minutes < 1440) {
// 大于等于60分钟且小于24小时1440分钟
double hours = minutes / 60.0;
if (fmod(hours, 1) == 0) {
// 如果能整除,不显示小数点
result[@"title"] = [NSString stringWithFormat:@"%ld小时", (long)hours];
} else {
// 如果不能整除,保留一位小数
result[@"title"] = [NSString stringWithFormat:@"%.1f小时", hours];
}
result[@"minutes"] = minutesString;
} else {
// 大于等于24小时
double days = minutes / 1440.0;
if (fmod(days, 1) == 0) {
// 如果能整除,不显示小数点
result[@"title"] = [NSString stringWithFormat:@"%ld天", (long)days];
} else {
// 如果不能整除,保留一位小数
result[@"title"] = [NSString stringWithFormat:@"%.1f天", days];
}
result[@"minutes"] = minutesString;
}
return result;
}
- (void)buildDurationDataSource {
NSMutableArray *arr = [NSMutableArray array];
for (NSString *duration in self.configModel.durations) {
[arr addObject:[self formatTimeWithString:duration]];
}
self.durationsOptions = arr.copy;
}
- (void)buildStartTimeSourceWithInitialDate:(NSDate *)date {
NSCalendar *calendar = [NSCalendar currentCalendar];
NSDate *now = [NSDate date];
// 最早:当前时间+24小时
NSDate *start = [calendar dateByAddingUnit:NSCalendarUnitHour
value:24
toDate:now
options:0];
// 最晚:当前时间+1个月
NSDateComponents *comp = [calendar components:NSCalendarUnitYear | NSCalendarUnitMonth | NSCalendarUnitDay fromDate:now];
comp.month += 1;
NSDate *end = [calendar dateFromComponents:comp];
self.minDate = start;
self.maxDate = end;
NSMutableArray *months = [NSMutableArray array];
NSMutableArray *days = [NSMutableArray array];
NSMutableArray *hours = [NSMutableArray array];
NSDate *iter = start;
while ([iter compare:end] != NSOrderedDescending) {
NSDateComponents *c = [calendar components:NSCalendarUnitMonth|NSCalendarUnitDay|NSCalendarUnitHour fromDate:iter];
NSString *monthStr = [NSString stringWithFormat:@"%02ld", (long)c.month];
NSString *dayStr = [NSString stringWithFormat:@"%02ld", (long)c.day];
NSString *hourStr = [NSString stringWithFormat:@"%02ld:00", (long)c.hour];
if (![months containsObject:monthStr]) [months addObject:monthStr];
if (![days containsObject:dayStr]) [days addObject:dayStr];
if (![hours containsObject:hourStr]) [hours addObject:hourStr];
iter = [calendar dateByAddingUnit:NSCalendarUnitHour value:1 toDate:iter options:0];
}
self.monthArray = months;
self.dayArray = days;
self.hourArray = hours;
self.selectedDate = start;
}
- (void)showInView:(UIView *)parentView
initialDate:(NSDate *)date
config:(EventConfigModel *)config
pickerType:(CreateEventPickerType)type
onConfirm:(void (^)(NSDate *date, NSString *resultString))onConfirm{
self.pickerType = type;
self.configModel = config;
self.onConfirmDate = onConfirm;
if (type == CreateEventPickerTypeStartTime) {
[self buildStartTimeSourceWithInitialDate:date];
_titleLabel.text = @"Start Time";
} else if (type == CreateEventPickerTypeDuration) {
[self buildDurationDataSource];
_titleLabel.text = @"Duration";
}
self.frame = parentView.bounds;
[parentView addSubview:self];
self.alpha = 0;
[self.pickerView reloadAllComponents];
[UIView animateWithDuration:0.25 animations:^{
self.alpha = 1;
}];
}
#pragma mark - UIPickerViewDataSource & Delegate
- (NSInteger)numberOfComponentsInPickerView:(UIPickerView *)pickerView {
switch (self.pickerType) {
case CreateEventPickerTypeStartTime:
return 3;
break;
case CreateEventPickerTypeDuration:
default:
return 1;
break;
}
}
- (NSInteger)pickerView:(UIPickerView *)pickerView numberOfRowsInComponent:(NSInteger)component {
switch (self.pickerType) {
case CreateEventPickerTypeStartTime: {
if (component == 0) return self.monthArray.count;
if (component == 1) return self.dayArray.count;
if (component == 2) return self.hourArray.count;
}
break;
case CreateEventPickerTypeDuration:
default:
return self.durationsOptions.count;
break;
}
return 0;
}
- (void)pickerView:(UIPickerView *)pickerView didSelectRow:(NSInteger)row inComponent:(NSInteger)component {
switch (self.pickerType) {
case CreateEventPickerTypeStartTime: {
NSInteger monthIdx = [pickerView selectedRowInComponent:0];
NSInteger dayIdx = [pickerView selectedRowInComponent:1];
NSInteger hourIdx = [pickerView selectedRowInComponent:2];
NSCalendar *calendar = [NSCalendar currentCalendar];
NSDateComponents *nowComp = [calendar components:NSCalendarUnitYear fromDate:[NSDate date]];
NSInteger year = nowComp.year;
NSInteger month = [self.monthArray[monthIdx] integerValue];
NSInteger day = [self.dayArray[dayIdx] integerValue];
NSInteger hour = [[self.hourArray[hourIdx] substringToIndex:2] integerValue];
NSDateComponents *selComp = [[NSDateComponents alloc] init];
selComp.year = year;
selComp.month = month;
selComp.day = day;
selComp.hour = hour;
selComp.minute = 0;
self.selectedDate = [calendar dateFromComponents:selComp];
}
break;
case CreateEventPickerTypeDuration: {
NSInteger minutes = [self.durationsOptions[row][@"minutes"] integerValue];
NSCalendar *calendar = [NSCalendar currentCalendar];
self.selectedDate = [calendar dateByAddingUnit:NSCalendarUnitMinute value:minutes toDate:[NSDate date] options:0];
}
break;
default:
break;
}
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
[pickerView reloadComponent:component];
});
}
- (UIView *)pickerView:(UIPickerView *)pickerView viewForRow:(NSInteger)row forComponent:(NSInteger)component reusingView:(UIView *)view {
NSInteger selectedRow = [pickerView selectedRowInComponent:component];
BOOL isSelectedRow = selectedRow == row;
NSString *content = @"";
switch (self.pickerType) {
case CreateEventPickerTypeStartTime: {
if (component == 0) content = self.monthArray[row];
if (component == 1) content = self.dayArray[row];
if (component == 2) content = self.hourArray[row];
}
break;
case CreateEventPickerTypeDuration:
content = self.durationsOptions[row][@"title"];
break;
default:
break;
}
UILabel *label = (UILabel *)view;
if (!label) {
label = [[UILabel alloc] init];
label.textAlignment = NSTextAlignmentCenter;
label.backgroundColor = [UIColor clearColor];
}
label.text = content;
label.font = isSelectedRow ? kFontMedium(15) : kFontRegular(12);
label.textColor = isSelectedRow ? UIColorFromRGB(0x313131) : UIColorFromRGB(0x7b7b7d);
return label;
}
- (CGFloat)pickerView:(UIPickerView *)pickerView rowHeightForComponent:(NSInteger)component {
return 30; // 设置行高
}
//- (NSAttributedString *)pickerView:(UIPickerView *)pickerView attributedTitleForRow:(NSInteger)row forComponent:(NSInteger)component {
// NSInteger selectedRow = [pickerView selectedRowInComponent:component];
// BOOL isSelectedRow = selectedRow == row;
// NSString *content = @"";
// switch (self.pickerType) {
// case CreateEventPickerTypeStartTime: {
// if (component == 0) content = self.monthArray[row];
// if (component == 1) content = self.dayArray[row];
// if (component == 2) content = self.hourArray[row];
// }
// break;
// case CreateEventPickerTypeDuration:
// content = self.durationsOptions[row][@"title"];
// break;
// default:
// break;
// }
//
// return [[NSAttributedString alloc] initWithString:content attributes:@{
// NSFontAttributeName: isSelectedRow ? kFontMedium(12) : kFontRegular(12),
// NSForegroundColorAttributeName: isSelectedRow ? UIColorFromRGB(0x313131) : UIColorFromRGB(0x7b7b7d)
// }];
//}
//- (UIView *)pickerView:(UIPickerView *)pickerView viewForRow:(NSInteger)row forComponent:(NSInteger)component reusingView:(UIView *)view {
// __block UILabel *label = (UILabel *)view;
//// dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
// if (!label) {
// label = [[UILabel alloc] init];
// label.textAlignment = NSTextAlignmentCenter;
// }
//
// NSString *content = @"";
// switch (self.pickerType) {
// case CreateEventPickerTypeStartTime: {
// if (component == 0) content = self.monthArray[row];
// if (component == 1) content = self.dayArray[row];
// if (component == 2) content = self.hourArray[row];
// }
// break;
// case CreateEventPickerTypeDuration:
// content = self.durationsOptions[row][@"title"];
// break;
// default:
// break;
// }
//
// label.text = content;
//
// // 设置选中和未选中状态的样式
// NSInteger selectedRow = [pickerView selectedRowInComponent:component];
// if (row == selectedRow) {
// label.textColor = UIColorFromRGB(0x313131);
// label.font = kFontMedium(15);
// } else {
// label.textColor = UIColorFromRGB(0x7b7b7d);
// label.font = kFontRegular(14);
// }
//// });
// return label;
//}
#pragma mark - Actions
- (void)okTapped {
if (self.onConfirmDate) {
NSString *resultString = @"";
switch (self.pickerType) {
case CreateEventPickerTypeStartTime: {
NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
formatter.dateFormat = @"yyyy-MM-dd HH:mm:ss";
resultString = [formatter stringFromDate:self.selectedDate];
}
break;
case CreateEventPickerTypeDuration: {
NSInteger selectedRow = [self.pickerView selectedRowInComponent:0];
resultString = self.durationsOptions[selectedRow][@"title"];
}
break;
default:
break;
}
self.onConfirmDate(self.selectedDate, resultString);
}
[self dismiss];
}
- (void)dismiss {
[UIView animateWithDuration:0.25 animations:^{
self.alpha = 0;
} completion:^(BOOL finished) {
[self removeFromSuperview];
}];
}
@end