Settings: remove 'Save' button

This commit is contained in:
giomfo 2014-11-10 15:26:37 +01:00
parent 9ee7508f21
commit 749a68585c
3 changed files with 229 additions and 150 deletions

View file

@ -721,7 +721,7 @@
<rect key="frame" x="0.0" y="64" width="600" height="100"/>
<autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
<subviews>
<button opaque="NO" contentMode="scaleAspectFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="5Dl-D7-ahX">
<button opaque="NO" contentMode="scaleAspectFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="5Dl-D7-ahX" userLabel="PicturePickerButton">
<rect key="frame" x="10" y="12" width="75" height="75"/>
<constraints>
<constraint firstAttribute="width" constant="75" id="hDj-ul-OgM"/>
@ -736,37 +736,26 @@
</connections>
</button>
<textField opaque="NO" clipsSubviews="YES" contentMode="scaleToFill" contentHorizontalAlignment="left" contentVerticalAlignment="center" borderStyle="roundedRect" placeholder="Your display name" minimumFontSize="17" translatesAutoresizingMaskIntoConstraints="NO" id="8M9-ZM-efS">
<rect key="frame" x="95" y="35" width="140" height="30"/>
<rect key="frame" x="95" y="35" width="495" height="30"/>
<fontDescription key="fontDescription" type="system" pointSize="14"/>
<textInputTraits key="textInputTraits" returnKeyType="done"/>
<connections>
<outlet property="delegate" destination="1TJ-Md-cjN" id="hV1-mY-vBI"/>
</connections>
</textField>
<button opaque="NO" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" buttonType="roundedRect" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="hjw-sm-lJ0">
<rect key="frame" x="551" y="34" width="39" height="33"/>
<fontDescription key="fontDescription" type="boldSystem" pointSize="17"/>
<state key="normal" title="Save">
<color key="titleShadowColor" white="0.5" alpha="1" colorSpace="calibratedWhite"/>
</state>
<connections>
<action selector="onButtonPressed:" destination="1TJ-Md-cjN" eventType="touchUpInside" id="TBD-Nx-SxA"/>
</connections>
</button>
<activityIndicatorView hidden="YES" opaque="NO" contentMode="scaleToFill" horizontalHuggingPriority="750" verticalHuggingPriority="750" hidesWhenStopped="YES" style="gray" translatesAutoresizingMaskIntoConstraints="NO" id="1H7-DG-oTV">
<rect key="frame" x="290" y="40" width="20" height="20"/>
</activityIndicatorView>
</subviews>
<color key="backgroundColor" white="1" alpha="1" colorSpace="calibratedWhite"/>
<constraints>
<constraint firstAttribute="centerY" secondItem="hjw-sm-lJ0" secondAttribute="centerY" id="2GV-E9-6cd"/>
<constraint firstAttribute="centerY" secondItem="1H7-DG-oTV" secondAttribute="centerY" id="3oK-Ie-SK8"/>
<constraint firstAttribute="centerY" secondItem="5Dl-D7-ahX" secondAttribute="centerY" id="8v6-O8-Rbm"/>
<constraint firstAttribute="trailing" secondItem="hjw-sm-lJ0" secondAttribute="trailing" constant="10" id="ABH-zI-08r"/>
<constraint firstAttribute="centerX" secondItem="1H7-DG-oTV" secondAttribute="centerX" id="IUT-eC-9SL"/>
<constraint firstAttribute="centerY" secondItem="8M9-ZM-efS" secondAttribute="centerY" id="M2X-FT-Qkb"/>
<constraint firstItem="5Dl-D7-ahX" firstAttribute="leading" secondItem="ZP5-e3-ge9" secondAttribute="leading" constant="10" id="bFJ-3g-wBh"/>
<constraint firstItem="8M9-ZM-efS" firstAttribute="leading" secondItem="5Dl-D7-ahX" secondAttribute="trailing" constant="10" id="hCS-JS-UW3"/>
<constraint firstAttribute="trailing" secondItem="8M9-ZM-efS" secondAttribute="trailing" constant="10" id="oL0-Kq-K48"/>
</constraints>
</view>
<prototypes>
@ -837,7 +826,6 @@
<navigationItem key="navigationItem" title="Settings" id="7NM-zW-wJT"/>
<connections>
<outlet property="activityIndicator" destination="1H7-DG-oTV" id="UEC-5U-M70"/>
<outlet property="saveBtn" destination="hjw-sm-lJ0" id="xN7-pc-PMD"/>
<outlet property="tableHeader" destination="ZP5-e3-ge9" id="nd0-lU-aW3"/>
<outlet property="tableView" destination="etG-ZU-b2r" id="5hz-jQ-qVT"/>
<outlet property="userDisplayName" destination="8M9-ZM-efS" id="rAQ-cX-3Ay"/>

View file

@ -95,6 +95,14 @@ static MatrixHandler *sharedHandler = nil;
//Alert user
[[AppDelegate theDelegate] showErrorAsAlert:error];
}];
// Request user's avatar
[self.mxRestClient avatarUrl:self.userId success:^(NSString *avatar_url) {
self.userPictureURL = avatar_url;
} failure:^(NSError *error) {
NSLog(@"Get picture url failed: %@", error);
//Alert user
[[AppDelegate theDelegate] showErrorAsAlert:error];
}];
self.mxSession = [[MXSession alloc] initWithMatrixRestClient:self.mxRestClient];
// Check here whether the app user wants to display all the events
@ -126,13 +134,36 @@ static MatrixHandler *sharedHandler = nil;
if (isLive) {
// Consider only event from app user
if ([event.userId isEqualToString:self.userId]) {
// Check whether this is a displayname change
if (event.prevContent) {
// Retrieve display name
NSString *prevDisplayname = event.prevContent[@"displayname"];
NSString *displayname = event.content[@"displayname"];
if (prevDisplayname && displayname && [displayname isEqualToString:prevDisplayname] == NO) {
if (!displayname.length) {
displayname = nil;
}
if (!prevDisplayname.length) {
prevDisplayname = nil;
}
// Check whether the display name has been changed
if ((displayname || prevDisplayname) && ([displayname isEqualToString:prevDisplayname] == NO)) {
// Update local storage
self.userDisplayName = displayname;
} else {
// Retrieve avatar url
NSString *avatar = event.content[@"avatar_url"];
NSString *prevAvatar = event.prevContent[@"avatar_url"];
if (!avatar.length) {
avatar = nil;
}
if (!prevAvatar.length) {
prevAvatar = nil;
}
// Check whether the avatar has been changed
if ((prevAvatar || avatar) && ([avatar isEqualToString:prevAvatar] == NO)) {
// Update local storage
self.userPictureURL = avatar;
}
}
}
}
@ -220,7 +251,9 @@ static MatrixHandler *sharedHandler = nil;
- (void)forceInitialSync {
[self closeSession];
notifyOpenSessionFailure = NO;
[self openSession];
if (self.accessToken) {
[self openSession];
}
}
- (void)enableEventsNotifications:(BOOL)isEnabled {
@ -290,6 +323,7 @@ static MatrixHandler *sharedHandler = nil;
// Reinitialize matrix handler
[self logout];
}
[[NSUserDefaults standardUserDefaults] synchronize];
}
- (NSString *)homeServer {
@ -302,6 +336,7 @@ static MatrixHandler *sharedHandler = nil;
} else {
[[NSUserDefaults standardUserDefaults] removeObjectForKey:@"homeserver"];
}
[[NSUserDefaults standardUserDefaults] synchronize];
}
- (NSString *)userLogin {
@ -314,6 +349,7 @@ static MatrixHandler *sharedHandler = nil;
} else {
[[NSUserDefaults standardUserDefaults] removeObjectForKey:@"userlogin"];
}
[[NSUserDefaults standardUserDefaults] synchronize];
}
- (NSString *)userId {
@ -326,6 +362,7 @@ static MatrixHandler *sharedHandler = nil;
} else {
[[NSUserDefaults standardUserDefaults] removeObjectForKey:@"userid"];
}
[[NSUserDefaults standardUserDefaults] synchronize];
}
- (NSString *)accessToken {
@ -340,6 +377,7 @@ static MatrixHandler *sharedHandler = nil;
[[NSUserDefaults standardUserDefaults] removeObjectForKey:@"accesstoken"];
[self closeSession];
}
[[NSUserDefaults standardUserDefaults] synchronize];
}
#pragma mark - Matrix user's settings
@ -355,6 +393,7 @@ static MatrixHandler *sharedHandler = nil;
// the app will look for this display name in incoming messages, it must not be nil.
[[NSUserDefaults standardUserDefaults] setObject:@"" forKey:@"userdisplayname"];
}
[[NSUserDefaults standardUserDefaults] synchronize];
}
- (NSString *)userPictureURL {
@ -367,6 +406,7 @@ static MatrixHandler *sharedHandler = nil;
} else {
[[NSUserDefaults standardUserDefaults] removeObjectForKey:@"userpictureurl"];
}
[[NSUserDefaults standardUserDefaults] synchronize];
}
#pragma mark - messages handler

View file

@ -36,20 +36,19 @@ NSString* const kCommandsDescriptionText = @"The following commands are availabl
NSString *currentDisplayName;
NSString *currentPictureURL;
BOOL shouldSavePicture;
NSString *uploadedPictureURL;
NSMutableArray *errorAlerts;
UIButton *logoutBtn;
UISwitch *notificationsSwitch;
UISwitch *allEventsSwitch;
UISwitch *sortMembersSwitch;
UIImagePickerController *imagePicker;
}
@property (strong, nonatomic) IBOutlet UITableView *tableView;
@property (weak, nonatomic) IBOutlet UIView *tableHeader;
@property (weak, nonatomic) IBOutlet UIButton *userPicture;
@property (weak, nonatomic) IBOutlet UITextField *userDisplayName;
@property (weak, nonatomic) IBOutlet UIButton *saveBtn;
@property (strong, nonatomic) IBOutlet UIActivityIndicatorView *activityIndicator;
- (IBAction)onButtonPressed:(id)sender;
@ -70,7 +69,9 @@ NSString* const kCommandsDescriptionText = @"The following commands are availabl
[logoutBtn addTarget:self action:@selector(onButtonPressed:) forControlEvents:UIControlEventTouchUpInside];
self.navigationItem.rightBarButtonItem = [[UIBarButtonItem alloc] initWithCustomView:logoutBtn];
[self reset];
errorAlerts = [NSMutableArray array];
[self startViewConfiguration];
}
- (void)didReceiveMemoryWarning {
@ -84,12 +85,21 @@ NSString* const kCommandsDescriptionText = @"The following commands are availabl
}
- (void)dealloc {
[[MatrixHandler sharedHandler] removeObserver:self forKeyPath:@"userDisplayName"];
[[MatrixHandler sharedHandler] removeObserver:self forKeyPath:@"userPictureURL"];
// Cancel picture loader (if any)
if (imageLoader) {
[MediaManager cancel:imageLoader];
imageLoader = nil;
}
// Cancel potential error alerts
for (CustomAlert *alert in errorAlerts){
[alert dismiss:NO];
}
errorAlerts = nil;
logoutBtn = nil;
notificationsSwitch = nil;
allEventsSwitch = nil;
@ -98,127 +108,14 @@ NSString* const kCommandsDescriptionText = @"The following commands are availabl
- (void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
// Ignore viewWillAppear if it is related to the mediaPicker use
if (imagePicker == nil) {
// Update User information
MatrixHandler *mxHandler = [MatrixHandler sharedHandler];
// Handle user's display name
currentDisplayName = mxHandler.userDisplayName;
self.userDisplayName.text = mxHandler.userDisplayName;
[[MatrixHandler sharedHandler] addObserver:self forKeyPath:@"userDisplayName" options:0 context:nil];
[mxHandler.mxRestClient displayName:mxHandler.mxRestClient.credentials.userId success:^(NSString *displayname) {
mxHandler.userDisplayName = displayname;
} failure:^(NSError *error) {
NSLog(@"Get displayName failed: %@", error);
//Alert user
[[AppDelegate theDelegate] showErrorAsAlert:error];
}];
// Handle user's picture url
[self updateUserPicture:mxHandler.userPictureURL];
[[MatrixHandler sharedHandler] addObserver:self forKeyPath:@"userPictureURL" options:0 context:nil];
[mxHandler.mxRestClient avatarUrl:mxHandler.mxRestClient.credentials.userId success:^(NSString *avatar_url) {
mxHandler.userPictureURL = avatar_url;
} failure:^(NSError *error) {
NSLog(@"Get picture url failed: %@", error);
//Alert user
[[AppDelegate theDelegate] showErrorAsAlert:error];
}];
// Refresh settings
[self.tableView reloadData];
}
}
- (void)viewWillDisappear:(BOOL)animated {
[super viewWillDisappear:animated];
// Ignore viewWillDisappear if it is related to the mediaPicker use
if (imagePicker == nil) {
[[MatrixHandler sharedHandler] removeObserver:self forKeyPath:@"userDisplayName"];
[[MatrixHandler sharedHandler] removeObserver:self forKeyPath:@"userPictureURL"];
shouldSavePicture = NO;
}
}
#pragma mark - Internal methods
- (void)save {
MatrixHandler *mxHandler = [MatrixHandler sharedHandler];
// Start saving
[_activityIndicator startAnimating];
_saveBtn.enabled = NO;
_saveBtn.alpha = 0.5;
// Check whether the display name has been changed
NSString *displayname = self.userDisplayName.text;
if ([displayname isEqualToString:currentDisplayName] == NO) {
// Save display name
[mxHandler.mxRestClient setDisplayName:displayname success:^{
currentDisplayName = displayname;
// Loop to save other changes
[self save];
} failure:^(NSError *error) {
// Stop saving
[_activityIndicator stopAnimating];
_saveBtn.enabled = YES;
_saveBtn.alpha = 1;
NSLog(@"Set displayName failed: %@", error);
//Alert user
[[AppDelegate theDelegate] showErrorAsAlert:error];
}];
// Wait for the end of this request before pursuing the saving
return;
}
// Check whether the picture has been changed
if (shouldSavePicture) {
[mxHandler.mxRestClient uploadContent:UIImageJPEGRepresentation([self.userPicture imageForState:UIControlStateNormal], 0.5)
mimeType:@"image/jpeg"
timeout:30
success:^(NSString *url) {
[mxHandler.mxRestClient setAvatarUrl:url
success:^{
shouldSavePicture = NO;
[MatrixHandler sharedHandler].userPictureURL = url;
// Loop to save other changes
[self save];
} failure:^(NSError *error) {
// Stop saving
[_activityIndicator stopAnimating];
_saveBtn.enabled = YES;
_saveBtn.alpha = 1;
NSLog(@"Set avatar url failed: %@", error);
//Alert user
[[AppDelegate theDelegate] showErrorAsAlert:error];
}];
} failure:^(NSError *error) {
// Stop saving
[_activityIndicator stopAnimating];
_saveBtn.enabled = YES;
_saveBtn.alpha = 1;
NSLog(@"Upload image failed: %@", error);
//Alert user
[[AppDelegate theDelegate] showErrorAsAlert:error];
}];
// Wait for the end of this request before pursuing the saving
return;
}
// Stop saving
[_activityIndicator stopAnimating];
_saveBtn.enabled = YES;
_saveBtn.alpha = 1;
}
- (void)reset {
// Cancel picture loader (if any)
if (imageLoader) {
@ -226,7 +123,13 @@ NSString* const kCommandsDescriptionText = @"The following commands are availabl
imageLoader = nil;
}
// Cancel potential error alerts
for (CustomAlert *alert in errorAlerts){
[alert dismiss:NO];
}
currentPictureURL = nil;
uploadedPictureURL = nil;
UIImage *image = [UIImage imageNamed:@"default-profile"];
[self.userPicture setImage:image forState:UIControlStateNormal];
[self.userPicture setImage:image forState:UIControlStateHighlighted];
@ -235,6 +138,158 @@ NSString* const kCommandsDescriptionText = @"The following commands are availabl
self.userDisplayName.text = nil;
}
- (void)startViewConfiguration {
// Initialize
[self reset];
// Set current user's information and add observers
MatrixHandler *mxHandler = [MatrixHandler sharedHandler];
[_activityIndicator startAnimating];
// Disable user's interactions
_userPicture.enabled = NO;
_userDisplayName.enabled = NO;
// Set user's display name
currentDisplayName = mxHandler.userDisplayName;
self.userDisplayName.text = mxHandler.userDisplayName;
[[MatrixHandler sharedHandler] addObserver:self forKeyPath:@"userDisplayName" options:0 context:nil];
[mxHandler.mxRestClient displayName:mxHandler.userId success:^(NSString *displayname) {
mxHandler.userDisplayName = displayname;
// Set user's picture url
[self updateUserPicture:mxHandler.userPictureURL];
[[MatrixHandler sharedHandler] addObserver:self forKeyPath:@"userPictureURL" options:0 context:nil];
[mxHandler.mxRestClient avatarUrl:mxHandler.userId success:^(NSString *avatar_url) {
mxHandler.userPictureURL = avatar_url;
[self endViewConfiguration];
} failure:^(NSError *error) {
NSLog(@"Get picture url failed: %@", error);
//Alert user
[[AppDelegate theDelegate] showErrorAsAlert:error];
[self endViewConfiguration];
}];
} failure:^(NSError *error) {
NSLog(@"Get displayName failed: %@", error);
//Alert user
[[AppDelegate theDelegate] showErrorAsAlert:error];
[self endViewConfiguration];
}];
}
- (void)endViewConfiguration {
[_activityIndicator stopAnimating];
_userPicture.enabled = YES;
_userDisplayName.enabled = YES;
[self.tableView reloadData];
}
- (void)saveDisplayName {
// Check whether the display name has been changed
NSString *displayname = self.userDisplayName.text;
if ([displayname isEqualToString:currentDisplayName] == NO) {
// Save display name
[_activityIndicator startAnimating];
_userDisplayName.enabled = NO;
MatrixHandler *mxHandler = [MatrixHandler sharedHandler];
[mxHandler.mxRestClient setDisplayName:displayname success:^{
currentDisplayName = displayname;
[_activityIndicator stopAnimating];
_userDisplayName.enabled = YES;
} failure:^(NSError *error) {
NSLog(@"Set displayName failed: %@", error);
[_activityIndicator stopAnimating];
_userDisplayName.enabled = YES;
//Alert user
NSString *title = [error.userInfo valueForKey:NSLocalizedFailureReasonErrorKey];
if (!title) {
title = @"Display name change failed";
}
NSString *msg = [error.userInfo valueForKey:NSLocalizedDescriptionKey];
CustomAlert *alert = [[CustomAlert alloc] initWithTitle:title message:msg style:CustomAlertStyleAlert];
[errorAlerts addObject:alert];
alert.cancelButtonIndex = [alert addActionWithTitle:@"Cancel" style:CustomAlertActionStyleDefault handler:^(CustomAlert *alert) {
[errorAlerts removeObject:alert];
// Remove change
self.userDisplayName.text = currentDisplayName;
}];
[alert addActionWithTitle:@"Retry" style:CustomAlertActionStyleDefault handler:^(CustomAlert *alert) {
[errorAlerts removeObject:alert];
[self saveDisplayName];
}];
[alert showInViewController:self];
}];
}
}
- (void)savePicture {
MatrixHandler *mxHandler = [MatrixHandler sharedHandler];
// Save picture
[_activityIndicator startAnimating];
_userPicture.enabled = NO;
if (uploadedPictureURL == nil) {
// Upload picture
[mxHandler.mxRestClient uploadContent:UIImageJPEGRepresentation([self.userPicture imageForState:UIControlStateNormal], 0.5)
mimeType:@"image/jpeg"
timeout:30
success:^(NSString *url) {
// Store uploaded picture url and trigger picture saving
uploadedPictureURL = url;
[self savePicture];
} failure:^(NSError *error) {
NSLog(@"Upload image failed: %@", error);
[_activityIndicator stopAnimating];
_userPicture.enabled = YES;
[self handleErrorDuringPictureSaving:error];
}];
} else {
[mxHandler.mxRestClient setAvatarUrl:uploadedPictureURL
success:^{
[MatrixHandler sharedHandler].userPictureURL = uploadedPictureURL;
uploadedPictureURL = nil;
[_activityIndicator stopAnimating];
_userPicture.enabled = YES;
} failure:^(NSError *error) {
NSLog(@"Set avatar url failed: %@", error);
[_activityIndicator stopAnimating];
_userPicture.enabled = YES;
[self handleErrorDuringPictureSaving:error];
}];
}
}
- (void)handleErrorDuringPictureSaving:(NSError*)error {
NSString *title = [error.userInfo valueForKey:NSLocalizedFailureReasonErrorKey];
if (!title) {
title = @"Picture change failed";
}
NSString *msg = [error.userInfo valueForKey:NSLocalizedDescriptionKey];
CustomAlert *alert = [[CustomAlert alloc] initWithTitle:title message:msg style:CustomAlertStyleAlert];
[errorAlerts addObject:alert];
alert.cancelButtonIndex = [alert addActionWithTitle:@"Cancel" style:CustomAlertActionStyleDefault handler:^(CustomAlert *alert) {
[errorAlerts removeObject:alert];
// Remove change
uploadedPictureURL = nil;
[self updateUserPicture:[MatrixHandler sharedHandler].userPictureURL];
}];
[alert addActionWithTitle:@"Retry" style:CustomAlertActionStyleDefault handler:^(CustomAlert *alert) {
[errorAlerts removeObject:alert];
[self savePicture];
}];
[alert showInViewController:self];
}
- (void)updateUserPicture:(NSString *)avatar_url {
if (currentPictureURL == nil || [currentPictureURL isEqualToString:avatar_url] == NO) {
// Cancel previous loader (if any)
@ -286,13 +341,11 @@ NSString* const kCommandsDescriptionText = @"The following commands are availabl
if (sender == _userPicture) {
// Open picture gallery
imagePicker = [[UIImagePickerController alloc] init];
imagePicker.delegate = self;
imagePicker.sourceType = UIImagePickerControllerSourceTypePhotoLibrary;
imagePicker.allowsEditing = NO;
[self presentViewController:imagePicker animated:YES completion:nil];
} else if (sender == _saveBtn) {
[self save];
UIImagePickerController *mediaPicker = [[UIImagePickerController alloc] init];
mediaPicker.delegate = self;
mediaPicker.sourceType = UIImagePickerControllerSourceTypePhotoLibrary;
mediaPicker.allowsEditing = NO;
[[AppDelegate theDelegate].masterTabBarController presentMediaPicker:mediaPicker];
} else if (sender == logoutBtn) {
[self reset];
[[AppDelegate theDelegate] logout];
@ -311,6 +364,8 @@ NSString* const kCommandsDescriptionText = @"The following commands are availabl
{
// Hide the keyboard
[_userDisplayName resignFirstResponder];
// Save display name change (if any)
[self saveDisplayName];
}
#pragma mark - UITextField delegate
@ -318,7 +373,7 @@ NSString* const kCommandsDescriptionText = @"The following commands are availabl
- (BOOL)textFieldShouldReturn:(UITextField*) textField
{
// "Done" key has been pressed
[textField resignFirstResponder];
[self dismissKeyboard];
return YES;
}
@ -436,7 +491,7 @@ NSString* const kCommandsDescriptionText = @"The following commands are availabl
if (selectedImage) {
[self.userPicture setImage:selectedImage forState:UIControlStateNormal];
[self.userPicture setImage:selectedImage forState:UIControlStateHighlighted];
shouldSavePicture = YES;
[self savePicture];
}
[self dismissMediaPicker];
}
@ -446,11 +501,7 @@ NSString* const kCommandsDescriptionText = @"The following commands are availabl
}
- (void)dismissMediaPicker {
if (imagePicker) {
[self dismissViewControllerAnimated:NO completion:nil];
imagePicker.delegate = nil;
imagePicker = nil;
}
[[AppDelegate theDelegate].masterTabBarController dismissMediaPicker];
}
@end