diff --git a/Signal/Images.xcassets/home_empty_splash_1.imageset/Contents.json b/Signal/Images.xcassets/home_empty_splash_1.imageset/Contents.json new file mode 100644 index 000000000..c89f86a30 --- /dev/null +++ b/Signal/Images.xcassets/home_empty_splash_1.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "idiom" : "universal", + "filename" : "human-1@3x.png", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "version" : 1, + "author" : "xcode" + } +} \ No newline at end of file diff --git a/Signal/Images.xcassets/home_empty_splash_1.imageset/human-1@3x.png b/Signal/Images.xcassets/home_empty_splash_1.imageset/human-1@3x.png new file mode 100644 index 000000000..ec9281204 Binary files /dev/null and b/Signal/Images.xcassets/home_empty_splash_1.imageset/human-1@3x.png differ diff --git a/Signal/Images.xcassets/home_empty_splash_2.imageset/Contents.json b/Signal/Images.xcassets/home_empty_splash_2.imageset/Contents.json new file mode 100644 index 000000000..14e1f9533 --- /dev/null +++ b/Signal/Images.xcassets/home_empty_splash_2.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "idiom" : "universal", + "filename" : "human-2@3x.png", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "version" : 1, + "author" : "xcode" + } +} \ No newline at end of file diff --git a/Signal/Images.xcassets/home_empty_splash_2.imageset/human-2@3x.png b/Signal/Images.xcassets/home_empty_splash_2.imageset/human-2@3x.png new file mode 100644 index 000000000..da3c87d0c Binary files /dev/null and b/Signal/Images.xcassets/home_empty_splash_2.imageset/human-2@3x.png differ diff --git a/Signal/Images.xcassets/home_empty_splash_3.imageset/Contents.json b/Signal/Images.xcassets/home_empty_splash_3.imageset/Contents.json new file mode 100644 index 000000000..4def99f09 --- /dev/null +++ b/Signal/Images.xcassets/home_empty_splash_3.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "idiom" : "universal", + "filename" : "human-3@3x.png", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "version" : 1, + "author" : "xcode" + } +} \ No newline at end of file diff --git a/Signal/Images.xcassets/home_empty_splash_3.imageset/human-3@3x.png b/Signal/Images.xcassets/home_empty_splash_3.imageset/human-3@3x.png new file mode 100644 index 000000000..dfb7a7653 Binary files /dev/null and b/Signal/Images.xcassets/home_empty_splash_3.imageset/human-3@3x.png differ diff --git a/Signal/Images.xcassets/home_empty_splash_4.imageset/Contents.json b/Signal/Images.xcassets/home_empty_splash_4.imageset/Contents.json new file mode 100644 index 000000000..9e9d460ad --- /dev/null +++ b/Signal/Images.xcassets/home_empty_splash_4.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "idiom" : "universal", + "filename" : "human-4@3x.png", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "version" : 1, + "author" : "xcode" + } +} \ No newline at end of file diff --git a/Signal/Images.xcassets/home_empty_splash_4.imageset/human-4@3x.png b/Signal/Images.xcassets/home_empty_splash_4.imageset/human-4@3x.png new file mode 100644 index 000000000..e04016de3 Binary files /dev/null and b/Signal/Images.xcassets/home_empty_splash_4.imageset/human-4@3x.png differ diff --git a/Signal/Images.xcassets/home_empty_splash_5.imageset/Contents.json b/Signal/Images.xcassets/home_empty_splash_5.imageset/Contents.json new file mode 100644 index 000000000..40f5f0350 --- /dev/null +++ b/Signal/Images.xcassets/home_empty_splash_5.imageset/Contents.json @@ -0,0 +1,21 @@ +{ + "images" : [ + { + "idiom" : "universal", + "filename" : "human-5@3x.png", + "scale" : "1x" + }, + { + "idiom" : "universal", + "scale" : "2x" + }, + { + "idiom" : "universal", + "scale" : "3x" + } + ], + "info" : { + "version" : 1, + "author" : "xcode" + } +} \ No newline at end of file diff --git a/Signal/Images.xcassets/home_empty_splash_5.imageset/human-5@3x.png b/Signal/Images.xcassets/home_empty_splash_5.imageset/human-5@3x.png new file mode 100644 index 000000000..546757997 Binary files /dev/null and b/Signal/Images.xcassets/home_empty_splash_5.imageset/human-5@3x.png differ diff --git a/Signal/src/ViewControllers/AppSettings/OWSLinkDeviceViewController.m b/Signal/src/ViewControllers/AppSettings/OWSLinkDeviceViewController.m index b704db862..3c72976f5 100644 --- a/Signal/src/ViewControllers/AppSettings/OWSLinkDeviceViewController.m +++ b/Signal/src/ViewControllers/AppSettings/OWSLinkDeviceViewController.m @@ -56,7 +56,7 @@ NS_ASSUME_NONNULL_BEGIN [self.qrScanningController.view autoPinEdgeToSuperviewEdge:ALEdgeLeading]; [self.qrScanningController.view autoPinEdgeToSuperviewEdge:ALEdgeTrailing]; [self.qrScanningController.view autoPinToTopLayoutGuideOfViewController:self withInset:0.f]; - [self.qrScanningController.view autoPinToAspectRatio:1.f]; + [self.qrScanningController.view autoPinToSquareAspectRatio]; UIView *bottomView = [UIView new]; [self.view addSubview:bottomView]; diff --git a/Signal/src/ViewControllers/HomeView/HomeViewController.m b/Signal/src/ViewControllers/HomeView/HomeViewController.m index 2e8ab8ba1..45b039133 100644 --- a/Signal/src/ViewControllers/HomeView/HomeViewController.m +++ b/Signal/src/ViewControllers/HomeView/HomeViewController.m @@ -7,6 +7,7 @@ #import "AppSettingsViewController.h" #import "HomeViewCell.h" #import "NewContactThreadViewController.h" +#import "OWS2FARegistrationViewController.h" #import "OWSNavigationController.h" #import "OWSPrimaryStorage.h" #import "ProfileViewController.h" @@ -24,6 +25,7 @@ #import #import #import +#import #import #import #import @@ -68,7 +70,7 @@ NSString *const kArchivedConversationsReuseIdentifier = @"kArchivedConversations OWSBlockListCacheDelegate> @property (nonatomic) UITableView *tableView; -@property (nonatomic) UILabel *emptyBoxLabel; +@property (nonatomic) UIView *emptyInboxView; @property (nonatomic) YapDatabaseConnection *editingDbConnection; @property (nonatomic) YapDatabaseConnection *uiDatabaseConnection; @@ -328,17 +330,42 @@ NSString *const kArchivedConversationsReuseIdentifier = @"kArchivedConversations self.tableView.rowHeight = UITableViewAutomaticDimension; self.tableView.estimatedRowHeight = 60; - UILabel *emptyBoxLabel = [UILabel new]; - self.emptyBoxLabel = emptyBoxLabel; - [self.view addSubview:emptyBoxLabel]; - - // Let the label use as many lines as needed. It will very rarely be more than 2 but may happen for verbose locs. - [emptyBoxLabel setNumberOfLines:0]; - emptyBoxLabel.lineBreakMode = NSLineBreakByWordWrapping; - - [emptyBoxLabel autoPinLeadingToSuperviewMargin]; - [emptyBoxLabel autoPinTrailingToSuperviewMargin]; - [emptyBoxLabel autoAlignAxisToSuperviewAxis:ALAxisHorizontal]; + NSArray *emptyInboxImageNames = @[ + @"home_empty_splash_1", + @"home_empty_splash_2", + @"home_empty_splash_3", + @"home_empty_splash_4", + @"home_empty_splash_5", + ]; + NSString *emptyInboxImageName = emptyInboxImageNames[arc4random_uniform((uint32_t) emptyInboxImageNames.count)]; + UIImageView *emptyInboxImageView = [UIImageView new]; + emptyInboxImageView.image = [UIImage imageNamed:emptyInboxImageName]; + emptyInboxImageView.layer.minificationFilter = kCAFilterTrilinear; + emptyInboxImageView.layer.magnificationFilter = kCAFilterTrilinear; + [emptyInboxImageView autoPinToAspectRatioWithSize:emptyInboxImageView.image.size]; + + UILabel *emptyInboxLabel = [UILabel new]; + emptyInboxLabel.text = NSLocalizedString(@"INBOX_VIEW_EMPTY_INBOX", + @"Message shown in the home view when the inbox is empty."); + emptyInboxLabel.font = UIFont.ows_dynamicTypeBodyFont; + emptyInboxLabel.textColor = Theme.secondaryColor; + emptyInboxLabel.textAlignment = NSTextAlignmentCenter; + emptyInboxLabel.numberOfLines = 0; + emptyInboxLabel.lineBreakMode = NSLineBreakByWordWrapping; + + UIStackView *emptyInboxStack = [[UIStackView alloc] initWithArrangedSubviews:@[ + emptyInboxImageView, + emptyInboxLabel, + ]]; + emptyInboxStack.axis = UILayoutConstraintAxisVertical; + emptyInboxStack.alignment = UIStackViewAlignmentCenter; + emptyInboxStack.spacing = 12; + emptyInboxStack.layoutMargins = UIEdgeInsetsMake(50, 50, 50, 50); + emptyInboxStack.layoutMarginsRelativeArrangement = YES; + self.emptyInboxView = emptyInboxStack; + [self.view addSubview:emptyInboxStack]; + [emptyInboxStack autoPinWidthToSuperviewMargins]; + [emptyInboxStack autoVCenterInSuperview]; UIRefreshControl *pullToRefreshView = [UIRefreshControl new]; pullToRefreshView.tintColor = [UIColor grayColor]; @@ -1445,67 +1472,14 @@ NSString *const kArchivedConversationsReuseIdentifier = @"kArchivedConversations NSUInteger archiveCount = self.numberOfArchivedThreads; if (self.homeViewMode == HomeViewMode_Inbox && inboxCount == 0 && archiveCount == 0) { - [self updateEmptyBoxText]; [_tableView setHidden:YES]; - [_emptyBoxLabel setHidden:NO]; - } else if (self.homeViewMode == HomeViewMode_Archive && archiveCount == 0) { - [self updateEmptyBoxText]; - [_tableView setHidden:YES]; - [_emptyBoxLabel setHidden:NO]; + [self.emptyInboxView setHidden:NO]; } else { - [_emptyBoxLabel setHidden:YES]; [_tableView setHidden:NO]; + [self.emptyInboxView setHidden:YES]; } } -- (void)updateEmptyBoxText -{ - // TODO: Theme, review with design. - _emptyBoxLabel.textColor = [UIColor grayColor]; - _emptyBoxLabel.font = [UIFont ows_regularFontWithSize:18.f]; - _emptyBoxLabel.textAlignment = NSTextAlignmentCenter; - - NSString *firstLine = @""; - NSString *secondLine = @""; - - if (self.homeViewMode == HomeViewMode_Inbox) { - if ([Environment.shared.preferences hasSentAMessage]) { - firstLine = NSLocalizedString( - @"EMPTY_INBOX_TITLE", @"Header text an existing user sees when viewing an empty inbox"); - secondLine = NSLocalizedString( - @"EMPTY_INBOX_TEXT", @"Body text an existing user sees when viewing an empty inbox"); - } else { - firstLine = NSLocalizedString( - @"EMPTY_INBOX_NEW_USER_TITLE", @"Header text a new user sees when viewing an empty inbox"); - secondLine = NSLocalizedString( - @"EMPTY_INBOX_NEW_USER_TEXT", @"Body text a new user sees when viewing an empty inbox"); - } - } else { - OWSAssertDebug(self.homeViewMode == HomeViewMode_Archive); - firstLine = NSLocalizedString( - @"EMPTY_ARCHIVE_TITLE", @"Header text an existing user sees when viewing an empty archive"); - secondLine = NSLocalizedString( - @"EMPTY_ARCHIVE_TEXT", @"Body text an existing user sees when viewing an empty archive"); - } - NSMutableAttributedString *fullLabelString = - [[NSMutableAttributedString alloc] initWithString:[NSString stringWithFormat:@"%@\n%@", firstLine, secondLine]]; - - [fullLabelString addAttribute:NSFontAttributeName - value:[UIFont ows_boldFontWithSize:15.f] - range:NSMakeRange(0, firstLine.length)]; - [fullLabelString addAttribute:NSFontAttributeName - value:[UIFont ows_regularFontWithSize:14.f] - range:NSMakeRange(firstLine.length + 1, secondLine.length)]; - [fullLabelString addAttribute:NSForegroundColorAttributeName - value:Theme.primaryColor - range:NSMakeRange(0, firstLine.length)]; - // TODO: Theme, Review with design. - [fullLabelString addAttribute:NSForegroundColorAttributeName - value:Theme.secondaryColor - range:NSMakeRange(firstLine.length + 1, secondLine.length)]; - _emptyBoxLabel.attributedText = fullLabelString; -} - // We want to delay asking for a review until an opportune time. // If the user has *just* launched Signal they intend to do something, we don't want to interrupt them. // If the user hasn't sent a message, we don't want to ask them for a review yet. diff --git a/Signal/src/views/RemoteVideoView.m b/Signal/src/views/RemoteVideoView.m index f0926155d..4104d5ad0 100644 --- a/Signal/src/views/RemoteVideoView.m +++ b/Signal/src/views/RemoteVideoView.m @@ -1,5 +1,5 @@ // -// Copyright (c) 2018 Open Whisper Systems. All rights reserved. +// Copyright (c) 2019 Open Whisper Systems. All rights reserved. // #import "RemoteVideoView.h" @@ -104,7 +104,6 @@ NS_ASSUME_NONNULL_BEGIN } CGFloat aspectRatio = remoteVideoSize.width / remoteVideoSize.height; - OWSLogVerbose(@"Remote video size: width: %f height: %f ratio: %f", remoteVideoSize.width, remoteVideoSize.height, @@ -125,7 +124,7 @@ NS_ASSUME_NONNULL_BEGIN // to approximate "scale to fill" contentMode // - Pin aspect ratio // - Width and height is *at least* as wide as superview - [constraints addObject:[videoView autoPinToAspectRatio:aspectRatio]]; + [constraints addObject:[videoView autoPinToAspectRatioWithSize:remoteVideoSize]]; [constraints addObject:[videoView autoSetDimension:ALDimensionWidth toSize:containingView.width relation:NSLayoutRelationGreaterThanOrEqual]]; diff --git a/Signal/translations/en.lproj/Localizable.strings b/Signal/translations/en.lproj/Localizable.strings index 667a5f55d..01dc21dc7 100644 --- a/Signal/translations/en.lproj/Localizable.strings +++ b/Signal/translations/en.lproj/Localizable.strings @@ -1122,6 +1122,9 @@ /* Label reminding the user that they are in archive mode. */ "INBOX_VIEW_ARCHIVE_MODE_REMINDER" = "These conversations are archived and will only appear in the Inbox if new messages are received."; +/* Message shown in the home view when the inbox is empty. */ +"INBOX_VIEW_EMPTY_INBOX" = "Give your inbox something to write home about. Get started by messaging a friend."; + /* Multi-line label explaining how to show names instead of phone numbers in your inbox */ "INBOX_VIEW_MISSING_CONTACTS_PERMISSION" = "You can enable contacts access in the iOS Settings app to see contact names in your Signal conversation list."; diff --git a/SignalMessaging/categories/UIView+OWS.h b/SignalMessaging/categories/UIView+OWS.h index 0c47facd0..7a775e6ef 100644 --- a/SignalMessaging/categories/UIView+OWS.h +++ b/SignalMessaging/categories/UIView+OWS.h @@ -41,6 +41,7 @@ CGFloat ScaleFromIPhone5(CGFloat iPhone5Value); - (void)autoPinHeightToHeightOfView:(UIView *)view; - (NSLayoutConstraint *)autoPinToSquareAspectRatio; +- (NSLayoutConstraint *)autoPinToAspectRatioWithSize:(CGSize)size; - (NSLayoutConstraint *)autoPinToAspectRatio:(CGFloat)ratio; #pragma mark - Content Hugging and Compression Resistance diff --git a/SignalMessaging/categories/UIView+OWS.m b/SignalMessaging/categories/UIView+OWS.m index a4999a0a3..8bdc03c17 100644 --- a/SignalMessaging/categories/UIView+OWS.m +++ b/SignalMessaging/categories/UIView+OWS.m @@ -142,6 +142,10 @@ CGFloat ScaleFromIPhone5(CGFloat iPhone5Value) return [self autoPinToAspectRatio:1.0]; } +- (NSLayoutConstraint *)autoPinToAspectRatioWithSize:(CGSize)size { + return [self autoPinToAspectRatio:size.width / size.height]; +} + - (NSLayoutConstraint *)autoPinToAspectRatio:(CGFloat)ratio { // Clamp to ensure view has reasonable aspect ratio.