diff --git a/Coding_iOS.xcodeproj/project.pbxproj b/Coding_iOS.xcodeproj/project.pbxproj index c4d100bd2..33eb354f1 100644 --- a/Coding_iOS.xcodeproj/project.pbxproj +++ b/Coding_iOS.xcodeproj/project.pbxproj @@ -1223,6 +1223,7 @@ B14689C21EE100B200B01371 /* vip_4_75@2x.png in Resources */ = {isa = PBXBuildFile; fileRef = B14689B21EE100B200B01371 /* vip_4_75@2x.png */; }; B14689C31EE100B200B01371 /* vip_4_75@3x.png in Resources */ = {isa = PBXBuildFile; fileRef = B14689B31EE100B200B01371 /* vip_4_75@3x.png */; }; B152ED4E2090B223004A6E8A /* ProjectSettingEntranceController.m in Sources */ = {isa = PBXBuildFile; fileRef = B152ED4D2090B223004A6E8A /* ProjectSettingEntranceController.m */; }; + B152ED542091B7CB004A6E8A /* ProjectArchiveViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = B152ED532091B7CB004A6E8A /* ProjectArchiveViewController.m */; }; B16EEF08208DDBB6005ABFD5 /* timeline_icon_read@3x.png in Resources */ = {isa = PBXBuildFile; fileRef = B16EEF06208DDBB5005ABFD5 /* timeline_icon_read@3x.png */; }; B16EEF09208DDBB6005ABFD5 /* timeline_icon_unread@3x.png in Resources */ = {isa = PBXBuildFile; fileRef = B16EEF07208DDBB6005ABFD5 /* timeline_icon_unread@3x.png */; }; B16EEF13209080D7005ABFD5 /* TaskBoardsViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = B16EEF12209080D7005ABFD5 /* TaskBoardsViewController.m */; }; @@ -3333,6 +3334,8 @@ B14689B31EE100B200B01371 /* vip_4_75@3x.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; path = "vip_4_75@3x.png"; sourceTree = ""; }; B152ED4C2090B223004A6E8A /* ProjectSettingEntranceController.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = ProjectSettingEntranceController.h; sourceTree = ""; }; B152ED4D2090B223004A6E8A /* ProjectSettingEntranceController.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = ProjectSettingEntranceController.m; sourceTree = ""; }; + B152ED522091B7CB004A6E8A /* ProjectArchiveViewController.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = ProjectArchiveViewController.h; sourceTree = ""; }; + B152ED532091B7CB004A6E8A /* ProjectArchiveViewController.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = ProjectArchiveViewController.m; sourceTree = ""; }; B16EEF06208DDBB5005ABFD5 /* timeline_icon_read@3x.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; path = "timeline_icon_read@3x.png"; sourceTree = ""; }; B16EEF07208DDBB6005ABFD5 /* timeline_icon_unread@3x.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; path = "timeline_icon_unread@3x.png"; sourceTree = ""; }; B16EEF11209080D7005ABFD5 /* TaskBoardsViewController.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = TaskBoardsViewController.h; sourceTree = ""; }; @@ -7035,6 +7038,8 @@ isa = PBXGroup; children = ( B9A00D7E1ACA3A05008BA008 /* ProjectSetting.storyboard */, + B152ED522091B7CB004A6E8A /* ProjectArchiveViewController.h */, + B152ED532091B7CB004A6E8A /* ProjectArchiveViewController.m */, B152ED4C2090B223004A6E8A /* ProjectSettingEntranceController.h */, B152ED4D2090B223004A6E8A /* ProjectSettingEntranceController.m */, B9A00D801ACA3A17008BA008 /* ProjectSettingViewController.h */, @@ -8529,6 +8534,7 @@ B12B64151FF0DE4800ACFDCC /* SkillCCell.m in Sources */, 4E94C4FF1B4D2B9300EB668A /* MenuButton.m in Sources */, B12B64091FE900D400ACFDCC /* AMPopTip+Draw.m in Sources */, + B152ED542091B7CB004A6E8A /* ProjectArchiveViewController.m in Sources */, 4ED4B49D1D8295F600EED8C6 /* TeamViewController.m in Sources */, 4EF3741C1BB1258600DDA662 /* LocalFileViewController.m in Sources */, 3A3878401AE295970078D5DE /* ResetLabelCell.m in Sources */, diff --git a/Coding_iOS/Controllers/ProjectSetting/ProjectArchiveViewController.h b/Coding_iOS/Controllers/ProjectSetting/ProjectArchiveViewController.h new file mode 100644 index 000000000..cd6dfa285 --- /dev/null +++ b/Coding_iOS/Controllers/ProjectSetting/ProjectArchiveViewController.h @@ -0,0 +1,17 @@ +// +// ProjectArchiveViewController.h +// Coding_iOS +// +// Created by Easeeeeeeeee on 2018/4/26. +// Copyright © 2018年 Coding. All rights reserved. +// + +#import +#import "Project.h" + +@interface ProjectArchiveViewController : UITableViewController + +@property (nonatomic, strong) Project *project; +@property (strong, nonatomic) IBOutletCollection(NSLayoutConstraint) NSArray *lines; + +@end diff --git a/Coding_iOS/Controllers/ProjectSetting/ProjectArchiveViewController.m b/Coding_iOS/Controllers/ProjectSetting/ProjectArchiveViewController.m new file mode 100644 index 000000000..1228ddfa4 --- /dev/null +++ b/Coding_iOS/Controllers/ProjectSetting/ProjectArchiveViewController.m @@ -0,0 +1,153 @@ +// +// ProjectArchiveViewController.m +// Coding_iOS +// +// Created by Easeeeeeeeee on 2018/4/26. +// Copyright © 2018年 Coding. All rights reserved. +// + +#import "ProjectArchiveViewController.h" +#import "Coding_NetAPIManager.h" + +#import +#import +#import +#import "ProjectDeleteAlertControllerVisualStyle.h" + +#import "Ease_2FA.h" + +@interface ProjectArchiveViewController () +@property (strong, nonatomic) SDCAlertController *alert; + +@end + +@implementation ProjectArchiveViewController + +- (void)viewDidLoad { + [super viewDidLoad]; + self.title = @"归档项目"; + + for (NSLayoutConstraint *cons in self.lines) { + cons.constant = 0.5; + } + + self.tableView.tableFooterView = [UIView new]; + [self.tableView setSeparatorColor:[UIColor colorWithRGBHex:0xe5e5e5]]; + self.tableView.backgroundColor = kColorTableSectionBg; +} + + +-(UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section{ + return [UIView new]; +} + +-(void)tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath +{ + [tableView addLineforPlainCell:cell forRowAtIndexPath:indexPath withLeftSpace:kPaddingLeftWidth]; +} + +-(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath{ + [tableView deselectRowAtIndexPath:indexPath animated:YES]; + if (indexPath.section != 1) { + return; + } + [[Coding_NetAPIManager sharedManager] request_VerifyTypeWithBlock:^(VerifyType type, NSError *error) { + if (!error) { + [self showArchiveAlertWithType:type]; + } + }]; +} + +- (void)showArchiveAlertWithType:(VerifyType)type{ + + if (self.alert) {//正在显示 + return; + } + + NSString *title, *message, *placeHolder; + if (type == VerifyTypePassword) { + title = @"需要验证密码"; + message = @"这是一个危险的操作,请提供登录密码确认!"; + placeHolder = @"请输入密码"; + }else if (type == VerifyTypeTotp){ + title = @"需要动态验证码"; + message = @"这是一个危险操作,需要进行身份验证!"; + placeHolder = @"请输入动态验证码"; + }else{//不知道啥类型,不处理 + return; + } + + _alert = [SDCAlertController alertControllerWithTitle:title message:message preferredStyle:SDCAlertControllerStyleAlert]; + + UITextField *passwordTextField = [[UITextField alloc] initWithFrame:CGRectMake(15, 0, 240.0, 30.0)]; + passwordTextField.leftView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, 5, 30)]; + passwordTextField.leftViewMode = UITextFieldViewModeAlways; + passwordTextField.layer.borderColor = [[UIColor lightGrayColor] colorWithAlphaComponent:0.6].CGColor; + passwordTextField.layer.borderWidth = 1; + passwordTextField.secureTextEntry = (type == VerifyTypePassword); + passwordTextField.backgroundColor = [UIColor whiteColor]; + passwordTextField.placeholder = placeHolder; + if (type == VerifyTypeTotp) { + passwordTextField.text = [OTPListViewController otpCodeWithGK:[Login curLoginUser].global_key]; + } + passwordTextField.delegate = self; + + [_alert.contentView addSubview:passwordTextField]; + + NSDictionary* passwordViews = NSDictionaryOfVariableBindings(passwordTextField); + + [_alert.contentView addConstraints:[NSLayoutConstraint constraintsWithVisualFormat:@"V:|-[passwordTextField]-(>=14)-|" options:0 metrics:nil views:passwordViews]]; + + // Style + _alert.visualStyle = [ProjectDeleteAlertControllerVisualStyle new]; + + // 添加密码框 + // [alert addTextFieldWithConfigurationHandler:^(UITextField *textField) { + // textField.secureTextEntry = YES; + // }]; + + // 添加按钮 + @weakify(self); + _alert.actionLayout = SDCAlertControllerActionLayoutHorizontal; + [_alert addAction:[SDCAlertAction actionWithTitle:@"取消" style:SDCAlertActionStyleDefault handler:^(SDCAlertAction *action) { + @strongify(self); + self.alert = nil; + }]]; + [_alert addAction:[SDCAlertAction actionWithTitle:@"确定" style:SDCAlertActionStyleDefault handler:^(SDCAlertAction *action) { + @strongify(self); + self.alert = nil; + NSString *passCode = passwordTextField.text; + if ([passCode length] > 0) { + // 归档项目 + [[Coding_NetAPIManager sharedManager] request_ArchiveProject_WithObj:self.project passCode:passCode type:type andBlock:^(Project *data, NSError *error) { + if (!error) { + [self.navigationController popToRootViewControllerAnimated:YES]; + } + }]; + } + }]]; + + [_alert presentWithCompletion:^{ + [passwordTextField becomeFirstResponder]; + }]; +} + + +-(BOOL)textFieldShouldReturn:(UITextField *)textField{ + [textField resignFirstResponder]; + return YES; +} + +#pragma mark - Orientations +- (BOOL)shouldAutorotate{ + return UIInterfaceOrientationIsLandscape(self.interfaceOrientation); +} + +- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation { + return UIInterfaceOrientationPortrait; +} + +- (UIInterfaceOrientationMask)supportedInterfaceOrientations { + return UIInterfaceOrientationMaskPortrait; +} +@end diff --git a/Coding_iOS/Controllers/ProjectSetting/ProjectSetting.storyboard b/Coding_iOS/Controllers/ProjectSetting/ProjectSetting.storyboard index 04c17a199..96699c342 100644 --- a/Coding_iOS/Controllers/ProjectSetting/ProjectSetting.storyboard +++ b/Coding_iOS/Controllers/ProjectSetting/ProjectSetting.storyboard @@ -91,7 +91,7 @@ - + @@ -107,205 +107,6 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - @@ -324,7 +125,7 @@ - - + @@ -513,8 +314,8 @@ - - + + @@ -563,7 +364,377 @@ - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/Coding_iOS/Controllers/ProjectSetting/ProjectSettingViewController.h b/Coding_iOS/Controllers/ProjectSetting/ProjectSettingViewController.h index fe611dcf0..5f1da443f 100644 --- a/Coding_iOS/Controllers/ProjectSetting/ProjectSettingViewController.h +++ b/Coding_iOS/Controllers/ProjectSetting/ProjectSettingViewController.h @@ -15,13 +15,12 @@ @property (nonatomic, strong) Project *project; -@property (strong, nonatomic) IBOutlet UILabel *projectNameLabel; +@property (weak, nonatomic) IBOutlet UITextField *projectNameF; @property (strong, nonatomic) IBOutlet UIImageView *projectImageView; @property (strong, nonatomic) IBOutlet UIPlaceHolderTextView *descTextView; @property (strong, nonatomic) IBOutletCollection(NSLayoutConstraint) NSArray *lines; @property (strong, nonatomic) IBOutlet UIImageView *privateImageView; -@property (strong, nonatomic) IBOutlet NSLayoutConstraint *privateIconLeftConstraint; @end diff --git a/Coding_iOS/Controllers/ProjectSetting/ProjectSettingViewController.m b/Coding_iOS/Controllers/ProjectSetting/ProjectSettingViewController.m index f84381317..eac3d9871 100644 --- a/Coding_iOS/Controllers/ProjectSetting/ProjectSettingViewController.m +++ b/Coding_iOS/Controllers/ProjectSetting/ProjectSettingViewController.m @@ -12,6 +12,7 @@ #import "Coding_NetAPIManager.h" #import "MBProgressHUD+Add.h" #import "JDStatusBarNotification.h" +#import "Coding_NetAPIManager.h" @interface ProjectSettingViewController () @@ -19,6 +20,8 @@ @interface ProjectSettingViewController ()= 90; +} + +- (BOOL)p_isOwner{ + return [self.project.owner_id isEqual:[Login curLoginUser].id]; +} + -(UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section{ return [UIView new]; } +- (CGFloat)tableView:(UITableView *)tableView heightForHeaderInSection:(NSInteger)section{ + if (section == 0) { + return [self p_isOwner]? 15: 0; + }else if (section == 1){ + return [self p_isOwner]? 15: 0; + }else{ + return [self p_isOwner]? 0: 15; + } +} + +- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section{ + if (section == 0) { + return [self p_canEditPro]? 2: 0; + }else if (section == 1){ + return [self p_isOwner]? 3: 0; + }else{ + return [self p_isOwner]? 0: 1; + } +} + -(void)tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath { [tableView addLineforPlainCell:cell forRowAtIndexPath:indexPath withLeftSpace:13]; @@ -172,6 +213,29 @@ -(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender{ [vc setValue:self.project forKey:@"project"]; } +- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath{ + [tableView deselectRowAtIndexPath:indexPath animated:YES]; + if (indexPath.section == 2) { + __weak typeof(self) weakSelf = self; + [[UIActionSheet bk_actionSheetCustomWithTitle:@"确定退出项目?" buttonTitles:nil destructiveTitle:@"确认退出" cancelTitle:@"取消" andDidDismissBlock:^(UIActionSheet *sheet, NSInteger index) { + if (index == 0) { + [weakSelf quitPro]; + } + }] showInView:self.view]; + } +} + +- (void)quitPro{ + ProjectMember *tempM = [ProjectMember new]; + tempM.user_id = [Login curLoginUser].id; + __weak typeof(self) weakSelf = self; + [[Coding_NetAPIManager sharedManager] request_ProjectMember_Quit:tempM andBlock:^(id data, NSError *error) { + if (data) { + [self.navigationController popToRootViewControllerAnimated:YES]; + } + }]; +} + #pragma mark - Orientations - (BOOL)shouldAutorotate{ return UIInterfaceOrientationIsLandscape(self.interfaceOrientation); diff --git a/Coding_iOS/Models/Project.h b/Coding_iOS/Models/Project.h index 398c73c24..dbe2d4d86 100644 --- a/Coding_iOS/Models/Project.h +++ b/Coding_iOS/Models/Project.h @@ -30,6 +30,8 @@ - (NSString *)toDeletePath; +- (NSString *)toArchivePath; + - (NSString *)toMembersPath; - (NSDictionary *)toMembersParams; diff --git a/Coding_iOS/Models/Project.m b/Coding_iOS/Models/Project.m index 36c799d4b..2db864e5b 100644 --- a/Coding_iOS/Models/Project.m +++ b/Coding_iOS/Models/Project.m @@ -134,6 +134,10 @@ -(NSString *)toDeletePath{ return [NSString stringWithFormat:@"api/user/%@/project/%@",self.owner_user_name, self.name]; } +- (NSString *)toArchivePath{ + return [NSString stringWithFormat:@"api/project/%@/archive", self.id]; +} + - (NSString *)toMembersPath{ if ([_id isKindOfClass:[NSNumber class]]) { return [NSString stringWithFormat:@"api/project/%d/members", self.id.intValue]; diff --git a/Coding_iOS/Util/Manager/Coding_NetAPIManager.h b/Coding_iOS/Util/Manager/Coding_NetAPIManager.h index fc09e4772..8ce9586f1 100755 --- a/Coding_iOS/Util/Manager/Coding_NetAPIManager.h +++ b/Coding_iOS/Util/Manager/Coding_NetAPIManager.h @@ -96,6 +96,7 @@ typedef NS_ENUM(NSInteger, PurposeType) { - (void)request_UpdateProject_WithObj:(Project *)project andBlock:(void (^)(Project *data, NSError *error))block; - (void)request_UpdateProject_WithObj:(Project *)project icon:(UIImage *)icon andBlock:(void (^)(id data, NSError *error))block progerssBlock:(void (^)(CGFloat progressValue))progress;; - (void)request_DeleteProject_WithObj:(Project *)project passCode:(NSString *)passCode type:(VerifyType)type andBlock:(void (^)(Project *data, NSError *error))block; +- (void)request_ArchiveProject_WithObj:(Project *)project passCode:(NSString *)passCode type:(VerifyType)type andBlock:(void (^)(Project *data, NSError *error))block; - (void)request_TransferProject:(Project *)project toUser:(User *)user passCode:(NSString *)passCode type:(VerifyType)type andBlock:(void (^)(Project *data, NSError *error))block; - (void)request_EditAliasOfMember:(ProjectMember *)curMember inProject:(Project *)curPro andBlock:(void (^)(id data, NSError *error))block; - (void)request_EditTypeOfMember:(ProjectMember *)curMember inProject:(Project *)curPro andBlock:(void (^)(id data, NSError *error))block; diff --git a/Coding_iOS/Util/Manager/Coding_NetAPIManager.m b/Coding_iOS/Util/Manager/Coding_NetAPIManager.m index 547b38f32..e1793e4bb 100644 --- a/Coding_iOS/Util/Manager/Coding_NetAPIManager.m +++ b/Coding_iOS/Util/Manager/Coding_NetAPIManager.m @@ -475,6 +475,21 @@ - (void)request_DeleteProject_WithObj:(Project *)project passCode:(NSString *)pa } }]; } +- (void)request_ArchiveProject_WithObj:(Project *)project passCode:(NSString *)passCode type:(VerifyType)type andBlock:(void (^)(Project *data, NSError *error))block{ + NSDictionary *params = @{@"two_factor_code": (type == VerifyTypePassword? [passCode sha1Str]: passCode)};; + [NSObject showStatusBarQueryStr:@"正在归档项目"]; + [[CodingNetAPIClient sharedJsonClient] requestJsonDataWithPath:[project toArchivePath] withParams:params withMethodType:Post andBlock:^(id data, NSError *error) { + if (data) { + [MobClick event:kUmeng_Event_Request_ActionOfServer label:@"归档项目"]; + + [NSObject showStatusBarSuccessStr:@"归档项目成功"]; + block(data, nil); + }else{ + [NSObject showStatusBarError:error]; + block(nil, error); + } + }]; +} - (void)request_TransferProject:(Project *)project toUser:(User *)user passCode:(NSString *)passCode type:(VerifyType)type andBlock:(void (^)(Project *data, NSError *error))block{ if (project.id.stringValue.length <= 0 || user.global_key.length <= 0|| passCode.length <= 0) {