From 67c89cb4e30924cd24f71851c975404fe1768c95 Mon Sep 17 00:00:00 2001 From: Matthew Chen Date: Fri, 15 Mar 2019 13:21:54 -0400 Subject: [PATCH] Ensure constant bubble sizes for oversize text. --- Signal.xcodeproj/project.pbxproj | 4 - .../Cells/OWSMessageBubbleView.m | 71 ++++----- .../ConversationView/ConversationViewItem.h | 3 +- .../ConversationView/ConversationViewItem.m | 93 ++++++++--- Signal/src/views/AttachmentPointerView.swift | 145 ------------------ 5 files changed, 107 insertions(+), 209 deletions(-) delete mode 100644 Signal/src/views/AttachmentPointerView.swift diff --git a/Signal.xcodeproj/project.pbxproj b/Signal.xcodeproj/project.pbxproj index 5b751d7eb..0dba75b4d 100644 --- a/Signal.xcodeproj/project.pbxproj +++ b/Signal.xcodeproj/project.pbxproj @@ -369,7 +369,6 @@ 452C468F1E427E200087B011 /* OutboundCallInitiator.swift in Sources */ = {isa = PBXBuildFile; fileRef = 452C468E1E427E200087B011 /* OutboundCallInitiator.swift */; }; 452C7CA72037628B003D51A5 /* Weak.swift in Sources */ = {isa = PBXBuildFile; fileRef = 45F170D51E315310003FC1F2 /* Weak.swift */; }; 452D1AF12081059C00A67F7F /* StringAdditionsTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = 452D1AF02081059C00A67F7F /* StringAdditionsTest.swift */; }; - 452EA09E1EA7ABE00078744B /* AttachmentPointerView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 452EA09D1EA7ABE00078744B /* AttachmentPointerView.swift */; }; 452EC6DF205E9E30000E787C /* MediaGalleryViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 452EC6DE205E9E30000E787C /* MediaGalleryViewController.swift */; }; 452EC6E1205FF5DC000E787C /* Bench.swift in Sources */ = {isa = PBXBuildFile; fileRef = 452EC6E0205FF5DC000E787C /* Bench.swift */; }; 452ECA4D1E087E7200E2F016 /* MessageFetcherJob.swift in Sources */ = {isa = PBXBuildFile; fileRef = 452ECA4C1E087E7200E2F016 /* MessageFetcherJob.swift */; }; @@ -1093,7 +1092,6 @@ 452B998F20A34B6B006F2F9E /* AddContactShareToExistingContactViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AddContactShareToExistingContactViewController.swift; sourceTree = ""; }; 452C468E1E427E200087B011 /* OutboundCallInitiator.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = OutboundCallInitiator.swift; sourceTree = ""; }; 452D1AF02081059C00A67F7F /* StringAdditionsTest.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = StringAdditionsTest.swift; sourceTree = ""; }; - 452EA09D1EA7ABE00078744B /* AttachmentPointerView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = AttachmentPointerView.swift; sourceTree = ""; }; 452EC6DE205E9E30000E787C /* MediaGalleryViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MediaGalleryViewController.swift; sourceTree = ""; }; 452EC6E0205FF5DC000E787C /* Bench.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Bench.swift; sourceTree = ""; }; 452ECA4C1E087E7200E2F016 /* MessageFetcherJob.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MessageFetcherJob.swift; sourceTree = ""; }; @@ -2419,7 +2417,6 @@ 76EB052B18170B33006006FC /* Views */ = { isa = PBXGroup; children = ( - 452EA09D1EA7ABE00078744B /* AttachmentPointerView.swift */, 34E3E5671EC4B19400495BAC /* AudioProgressView.swift */, 4C2F454E214C00E1004871FF /* AvatarTableViewCell.swift */, 4CA46F4B219CCC630038ABDE /* CaptionView.swift */, @@ -3602,7 +3599,6 @@ 34B3F87B1E8DF1700035BE1A /* ExperienceUpgradesPageViewController.swift in Sources */, 3448E1622213585C004B052E /* OnboardingBaseViewController.swift in Sources */, 34E5DC8220D8050D00C08145 /* RegistrationUtils.m in Sources */, - 452EA09E1EA7ABE00078744B /* AttachmentPointerView.swift in Sources */, 45638BDC1F3DD0D400128435 /* DebugUICalling.swift in Sources */, 34E3E5681EC4B19400495BAC /* AudioProgressView.swift in Sources */, 34D1F0521F7E8EA30066283D /* GiphyDownloader.swift in Sources */, diff --git a/Signal/src/ViewControllers/ConversationView/Cells/OWSMessageBubbleView.m b/Signal/src/ViewControllers/ConversationView/Cells/OWSMessageBubbleView.m index 28643adae..246363ea4 100644 --- a/Signal/src/ViewControllers/ConversationView/Cells/OWSMessageBubbleView.m +++ b/Signal/src/ViewControllers/ConversationView/Cells/OWSMessageBubbleView.m @@ -274,15 +274,16 @@ const UIDataDetectorTypes kOWSAllowedDataDetectorTypes case OWSMessageCellType_GenericAttachment: bodyMediaView = [self loadViewForGenericAttachment]; break; - case OWSMessageCellType_DownloadingAttachment: - bodyMediaView = [self loadViewForDownloadingAttachment]; - break; case OWSMessageCellType_ContactShare: bodyMediaView = [self loadViewForContactShare]; break; case OWSMessageCellType_MediaMessage: bodyMediaView = [self loadViewForMediaAlbum]; break; + case OWSMessageCellType_OversizeTextDownloading: + case OWSMessageCellType_OversizeTextFailed: + bodyMediaView = [self loadViewForOversizeTextDownload]; + break; } if (bodyMediaView) { @@ -564,8 +565,9 @@ const UIDataDetectorTypes kOWSAllowedDataDetectorTypes case OWSMessageCellType_TextOnlyMessage: case OWSMessageCellType_Audio: case OWSMessageCellType_GenericAttachment: - case OWSMessageCellType_DownloadingAttachment: case OWSMessageCellType_ContactShare: + case OWSMessageCellType_OversizeTextDownloading: + case OWSMessageCellType_OversizeTextFailed: return NO; case OWSMessageCellType_MediaMessage: return YES; @@ -579,9 +581,10 @@ const UIDataDetectorTypes kOWSAllowedDataDetectorTypes return NO; case OWSMessageCellType_Audio: case OWSMessageCellType_GenericAttachment: - case OWSMessageCellType_DownloadingAttachment: case OWSMessageCellType_ContactShare: case OWSMessageCellType_MediaMessage: + case OWSMessageCellType_OversizeTextDownloading: + case OWSMessageCellType_OversizeTextFailed: return YES; } } @@ -870,31 +873,6 @@ const UIDataDetectorTypes kOWSAllowedDataDetectorTypes return attachmentView; } -- (UIView *)loadViewForDownloadingAttachment -{ - OWSAssertDebug(self.viewItem.attachmentPointer); - - // TODO: We probably want to do something different for attachments - // being restored from backup. - AttachmentPointerView *downloadView = - [[AttachmentPointerView alloc] initWithAttachmentPointer:self.viewItem.attachmentPointer - isIncoming:self.isIncoming - conversationStyle:self.conversationStyle]; - - UIView *wrapper = [UIView new]; - [wrapper addSubview:downloadView]; - [downloadView autoPinEdgesToSuperviewEdges]; - - self.loadCellContentBlock = ^{ - // Do nothing. - }; - self.unloadCellContentBlock = ^{ - // Do nothing. - }; - - return wrapper; -} - - (UIView *)loadViewForContactShare { OWSAssertDebug(self.viewItem.contactShare); @@ -915,6 +893,26 @@ const UIDataDetectorTypes kOWSAllowedDataDetectorTypes return contactShareView; } +- (UIView *)loadViewForOversizeTextDownload +{ + BOOL isFailed = self.cellType == OWSMessageCellType_OversizeTextFailed; + + // We can use an empty view. The progress views will display download + // progress or tap-to-retry UI. + UIView *attachmentView = [UIView new]; + + [self addProgressViewsIfNecessary:attachmentView]; + + self.loadCellContentBlock = ^{ + // Do nothing. + }; + self.unloadCellContentBlock = ^{ + // Do nothing. + }; + + return attachmentView; +} + - (void)addProgressViewsIfNecessary:(UIView *)bodyMediaView { if (self.viewItem.attachmentStream) { @@ -1075,9 +1073,6 @@ const UIDataDetectorTypes kOWSAllowedDataDetectorTypes result = [attachmentView measureSizeWithMaxMessageWidth:maxMessageWidth]; break; } - case OWSMessageCellType_DownloadingAttachment: - result = CGSizeMake(MIN(200, maxMessageWidth), [AttachmentPointerView measureHeight]); - break; case OWSMessageCellType_ContactShare: OWSAssertDebug(self.viewItem.contactShare); @@ -1122,6 +1117,12 @@ const UIDataDetectorTypes kOWSAllowedDataDetectorTypes } } break; + case OWSMessageCellType_OversizeTextDownloading: + case OWSMessageCellType_OversizeTextFailed: + // There's no way to predict the size of the oversize text, + // so we just use a square bubble. + result = CGSizeMake(maxMessageWidth, maxMessageWidth); + break; } OWSAssertDebug(result.width <= maxMessageWidth); @@ -1462,6 +1463,8 @@ const UIDataDetectorTypes kOWSAllowedDataDetectorTypes switch (self.cellType) { case OWSMessageCellType_Unknown: case OWSMessageCellType_TextOnlyMessage: + case OWSMessageCellType_OversizeTextDownloading: + case OWSMessageCellType_OversizeTextFailed: break; case OWSMessageCellType_Audio: if (self.viewItem.attachmentStream) { @@ -1473,8 +1476,6 @@ const UIDataDetectorTypes kOWSAllowedDataDetectorTypes [AttachmentSharing showShareUIForAttachment:self.viewItem.attachmentStream]; } break; - case OWSMessageCellType_DownloadingAttachment: - break; case OWSMessageCellType_ContactShare: [self.delegate didTapContactShareViewItem:self.viewItem]; break; diff --git a/Signal/src/ViewControllers/ConversationView/ConversationViewItem.h b/Signal/src/ViewControllers/ConversationView/ConversationViewItem.h index 3ec982aeb..b82272eaa 100644 --- a/Signal/src/ViewControllers/ConversationView/ConversationViewItem.h +++ b/Signal/src/ViewControllers/ConversationView/ConversationViewItem.h @@ -12,9 +12,10 @@ typedef NS_ENUM(NSInteger, OWSMessageCellType) { OWSMessageCellType_TextOnlyMessage, OWSMessageCellType_Audio, OWSMessageCellType_GenericAttachment, - OWSMessageCellType_DownloadingAttachment, OWSMessageCellType_ContactShare, OWSMessageCellType_MediaMessage, + OWSMessageCellType_OversizeTextDownloading, + OWSMessageCellType_OversizeTextFailed, }; NSString *NSStringForOWSMessageCellType(OWSMessageCellType cellType); diff --git a/Signal/src/ViewControllers/ConversationView/ConversationViewItem.m b/Signal/src/ViewControllers/ConversationView/ConversationViewItem.m index c486ebb82..180eef15e 100644 --- a/Signal/src/ViewControllers/ConversationView/ConversationViewItem.m +++ b/Signal/src/ViewControllers/ConversationView/ConversationViewItem.m @@ -26,14 +26,16 @@ NSString *NSStringForOWSMessageCellType(OWSMessageCellType cellType) return @"OWSMessageCellType_Audio"; case OWSMessageCellType_GenericAttachment: return @"OWSMessageCellType_GenericAttachment"; - case OWSMessageCellType_DownloadingAttachment: - return @"OWSMessageCellType_DownloadingAttachment"; case OWSMessageCellType_Unknown: return @"OWSMessageCellType_Unknown"; case OWSMessageCellType_ContactShare: return @"OWSMessageCellType_ContactShare"; case OWSMessageCellType_MediaMessage: return @"OWSMessageCellType_MediaMessage"; + case OWSMessageCellType_OversizeTextDownloading: + return @"OWSMessageCellType_OversizeTextDownloading"; + case OWSMessageCellType_OversizeTextFailed: + return @"OWSMessageCellType_OversizeTextFailed"; } } @@ -591,10 +593,18 @@ NSString *NSStringForOWSMessageCellType(OWSMessageCellType cellType) } TSAttachment *_Nullable oversizeTextAttachment = [message oversizeTextAttachmentWithTransaction:transaction]; - if (oversizeTextAttachment != nil && [oversizeTextAttachment isKindOfClass:[TSAttachmentStream class]]) { + if ([oversizeTextAttachment isKindOfClass:[TSAttachmentStream class]]) { TSAttachmentStream *oversizeTextAttachmentStream = (TSAttachmentStream *)oversizeTextAttachment; self.displayableBodyText = [self displayableBodyTextForOversizeTextAttachment:oversizeTextAttachmentStream interactionId:message.uniqueId]; + } else if ([oversizeTextAttachment isKindOfClass:[TSAttachmentPointer class]]) { + TSAttachmentPointer *oversizeTextAttachmentPointer = (TSAttachmentPointer *)oversizeTextAttachment; + // TODO: Handle backup restore. + self.messageCellType = (oversizeTextAttachmentPointer.state == TSAttachmentPointerStateFailed + ? OWSMessageCellType_OversizeTextFailed + : OWSMessageCellType_OversizeTextDownloading); + self.attachmentPointer = (TSAttachmentPointer *)oversizeTextAttachmentPointer; + return; } else { NSString *_Nullable bodyText = [message bodyTextWithTransaction:transaction]; if (bodyText) { @@ -860,6 +870,11 @@ NSString *NSStringForOWSMessageCellType(OWSMessageCellType cellType) - (void)copyTextAction { + if (self.attachmentPointer != nil) { + OWSFailDebug(@"Can't copy not-yet-downloaded attachment"); + return; + } + switch (self.messageCellType) { case OWSMessageCellType_TextOnlyMessage: case OWSMessageCellType_Audio: @@ -869,10 +884,6 @@ NSString *NSStringForOWSMessageCellType(OWSMessageCellType cellType) [UIPasteboard.generalPasteboard setString:self.displayableBodyText.fullText]; break; } - case OWSMessageCellType_DownloadingAttachment: { - OWSFailDebug(@"Can't copy not-yet-downloaded attachment"); - break; - } case OWSMessageCellType_Unknown: { OWSFailDebug(@"No text to copy"); break; @@ -882,11 +893,20 @@ NSString *NSStringForOWSMessageCellType(OWSMessageCellType cellType) OWSFailDebug(@"Not implemented yet"); break; } + case OWSMessageCellType_OversizeTextDownloading: + case OWSMessageCellType_OversizeTextFailed: + OWSFailDebug(@"Can't copy not-yet-downloaded attachment"); + return; } } - (void)copyMediaAction { + if (self.attachmentPointer != nil) { + OWSFailDebug(@"Can't copy not-yet-downloaded attachment"); + return; + } + switch (self.messageCellType) { case OWSMessageCellType_Unknown: case OWSMessageCellType_TextOnlyMessage: @@ -899,10 +919,6 @@ NSString *NSStringForOWSMessageCellType(OWSMessageCellType cellType) [self copyAttachmentToPasteboard:self.attachmentStream]; break; } - case OWSMessageCellType_DownloadingAttachment: { - OWSFailDebug(@"Can't copy not-yet-downloaded attachment"); - break; - } case OWSMessageCellType_MediaMessage: { if (self.mediaAlbumItems.count == 1) { ConversationMediaAlbumItem *mediaAlbumItem = self.mediaAlbumItems.firstObject; @@ -915,6 +931,10 @@ NSString *NSStringForOWSMessageCellType(OWSMessageCellType cellType) OWSFailDebug(@"Can't copy media album"); break; } + case OWSMessageCellType_OversizeTextDownloading: + case OWSMessageCellType_OversizeTextFailed: + OWSFailDebug(@"Can't copy not-yet-downloaded attachment"); + return; } } @@ -937,6 +957,11 @@ NSString *NSStringForOWSMessageCellType(OWSMessageCellType cellType) - (void)shareMediaAction { + if (self.attachmentPointer != nil) { + OWSFailDebug(@"Can't share not-yet-downloaded attachment"); + return; + } + switch (self.messageCellType) { case OWSMessageCellType_Unknown: case OWSMessageCellType_TextOnlyMessage: @@ -947,10 +972,6 @@ NSString *NSStringForOWSMessageCellType(OWSMessageCellType cellType) case OWSMessageCellType_GenericAttachment: [AttachmentSharing showShareUIForAttachment:self.attachmentStream]; break; - case OWSMessageCellType_DownloadingAttachment: { - OWSFailDebug(@"Can't share not-yet-downloaded attachment"); - break; - } case OWSMessageCellType_MediaMessage: { // TODO: We need a "canShareMediaAction" method. OWSAssertDebug(self.mediaAlbumItems); @@ -967,11 +988,19 @@ NSString *NSStringForOWSMessageCellType(OWSMessageCellType cellType) [AttachmentSharing showShareUIForAttachments:attachmentStreams completion:nil]; break; } + case OWSMessageCellType_OversizeTextDownloading: + case OWSMessageCellType_OversizeTextFailed: + OWSFailDebug(@"Can't share not-yet-downloaded attachment"); + return; } } - (BOOL)canCopyMedia { + if (self.attachmentPointer != nil) { + return NO; + } + switch (self.messageCellType) { case OWSMessageCellType_Unknown: case OWSMessageCellType_TextOnlyMessage: @@ -980,7 +1009,6 @@ NSString *NSStringForOWSMessageCellType(OWSMessageCellType cellType) case OWSMessageCellType_Audio: return NO; case OWSMessageCellType_GenericAttachment: - case OWSMessageCellType_DownloadingAttachment: case OWSMessageCellType_MediaMessage: { if (self.mediaAlbumItems.count == 1) { ConversationMediaAlbumItem *mediaAlbumItem = self.mediaAlbumItems.firstObject; @@ -990,11 +1018,18 @@ NSString *NSStringForOWSMessageCellType(OWSMessageCellType cellType) } return NO; } + case OWSMessageCellType_OversizeTextDownloading: + case OWSMessageCellType_OversizeTextFailed: + return NO; } } - (BOOL)canSaveMedia { + if (self.attachmentPointer != nil) { + return NO; + } + switch (self.messageCellType) { case OWSMessageCellType_Unknown: case OWSMessageCellType_TextOnlyMessage: @@ -1003,7 +1038,6 @@ NSString *NSStringForOWSMessageCellType(OWSMessageCellType cellType) case OWSMessageCellType_Audio: return NO; case OWSMessageCellType_GenericAttachment: - case OWSMessageCellType_DownloadingAttachment: return NO; case OWSMessageCellType_MediaMessage: { for (ConversationMediaAlbumItem *mediaAlbumItem in self.mediaAlbumItems) { @@ -1025,11 +1059,18 @@ NSString *NSStringForOWSMessageCellType(OWSMessageCellType cellType) } return NO; } + case OWSMessageCellType_OversizeTextDownloading: + case OWSMessageCellType_OversizeTextFailed: + return NO; } } - (void)saveMediaAction { + if (self.attachmentPointer != nil) { + OWSFailDebug(@"Can't save not-yet-downloaded attachment"); + return; + } switch (self.messageCellType) { case OWSMessageCellType_Unknown: case OWSMessageCellType_TextOnlyMessage: @@ -1042,14 +1083,14 @@ NSString *NSStringForOWSMessageCellType(OWSMessageCellType cellType) case OWSMessageCellType_GenericAttachment: OWSFailDebug(@"Cannot save media data."); break; - case OWSMessageCellType_DownloadingAttachment: { - OWSFailDebug(@"Can't save not-yet-downloaded attachment"); - break; - } case OWSMessageCellType_MediaMessage: { [self saveMediaAlbumItems]; break; } + case OWSMessageCellType_OversizeTextDownloading: + case OWSMessageCellType_OversizeTextFailed: + OWSFailDebug(@"Can't save not-yet-downloaded attachment"); + return; } } @@ -1112,6 +1153,10 @@ NSString *NSStringForOWSMessageCellType(OWSMessageCellType cellType) - (BOOL)hasMediaActionContent { + if (self.attachmentPointer != nil) { + return NO; + } + switch (self.messageCellType) { case OWSMessageCellType_Unknown: case OWSMessageCellType_TextOnlyMessage: @@ -1120,11 +1165,11 @@ NSString *NSStringForOWSMessageCellType(OWSMessageCellType cellType) case OWSMessageCellType_Audio: case OWSMessageCellType_GenericAttachment: return self.attachmentStream != nil; - case OWSMessageCellType_DownloadingAttachment: { - return NO; - } case OWSMessageCellType_MediaMessage: return self.firstValidAlbumAttachment != nil; + case OWSMessageCellType_OversizeTextDownloading: + case OWSMessageCellType_OversizeTextFailed: + return NO; } } diff --git a/Signal/src/views/AttachmentPointerView.swift b/Signal/src/views/AttachmentPointerView.swift deleted file mode 100644 index ada2e7c97..000000000 --- a/Signal/src/views/AttachmentPointerView.swift +++ /dev/null @@ -1,145 +0,0 @@ -// -// Copyright (c) 2018 Open Whisper Systems. All rights reserved. -// - -import Foundation -import SignalServiceKit -import SignalMessaging - -class AttachmentPointerView: UIStackView { - - let isIncoming: Bool - let attachmentPointer: TSAttachmentPointer - let conversationStyle: ConversationStyle - - let progressView = OWSProgressView() - let nameLabel = UILabel() - let statusLabel = UILabel() - let filename: String - let genericFilename = NSLocalizedString("ATTACHMENT_DEFAULT_FILENAME", comment: "Generic filename for an attachment with no known name") - - var progress: CGFloat = 0 { - didSet { - self.progressView.progress = progress - } - } - - @objc - required init(attachmentPointer: TSAttachmentPointer, isIncoming: Bool, conversationStyle: ConversationStyle) { - self.attachmentPointer = attachmentPointer - self.isIncoming = isIncoming - self.conversationStyle = conversationStyle - - let attachmentPointerFilename = attachmentPointer.sourceFilename - if let filename = attachmentPointerFilename, !filename.isEmpty { - self.filename = filename - } else { - self.filename = genericFilename - } - - super.init(frame: CGRect.zero) - - createSubviews() - updateViews() - - if attachmentPointer.state == .downloading { - NotificationCenter.default.addObserver(self, - selector: #selector(attachmentDownloadProgress(_:)), - name: NSNotification.Name.attachmentDownloadProgress, - object: nil) - } - } - - deinit { - NotificationCenter.default.removeObserver(self) - } - - @objc internal func attachmentDownloadProgress(_ notification: Notification) { - guard let attachmentId = attachmentPointer.uniqueId else { - owsFailDebug("Missing attachment id.") - return - } - guard let progress = (notification as NSNotification).userInfo?[kAttachmentDownloadProgressKey] as? NSNumber else { - owsFailDebug("Attachment download notification missing progress.") - return - } - guard let notificationAttachmentId = (notification as NSNotification).userInfo?[kAttachmentDownloadAttachmentIDKey] as? String else { - owsFailDebug("Attachment download notification missing attachment id.") - return - } - guard notificationAttachmentId == attachmentId else { - return - } - self.progress = CGFloat(progress.floatValue) - } - - @available(*, unavailable, message: "use init(call:) constructor instead.") - required init(coder aDecoder: NSCoder) { - notImplemented() - } - - private static var vSpacing: CGFloat = 5 - private class func nameFont() -> UIFont { return UIFont.ows_dynamicTypeBody } - private class func statusFont() -> UIFont { return UIFont.ows_dynamicTypeCaption1 } - private static var progressWidth: CGFloat = 80 - private static var progressHeight: CGFloat = 6 - - func createSubviews() { - progressView.autoSetDimension(.width, toSize: AttachmentPointerView.progressWidth) - progressView.autoSetDimension(.height, toSize: AttachmentPointerView.progressHeight) - - // truncate middle to be sure we include file extension - nameLabel.lineBreakMode = .byTruncatingMiddle - nameLabel.textAlignment = .center - nameLabel.textColor = self.textColor - nameLabel.font = AttachmentPointerView.nameFont() - - statusLabel.textAlignment = .center - statusLabel.adjustsFontSizeToFitWidth = true - statusLabel.numberOfLines = 2 - statusLabel.textColor = self.textColor - statusLabel.font = AttachmentPointerView.statusFont() - - self.axis = .vertical - self.spacing = AttachmentPointerView.vSpacing - addArrangedSubview(nameLabel) - addArrangedSubview(progressView) - addArrangedSubview(statusLabel) - } - - func updateViews() { - let emoji = TSAttachment.emoji(forMimeType: self.attachmentPointer.contentType) - nameLabel.text = "\(emoji) \(self.filename)" - - statusLabel.text = { - switch self.attachmentPointer.state { - case .enqueued: - return NSLocalizedString("ATTACHMENT_DOWNLOADING_STATUS_QUEUED", comment: "Status label when an attachment is enqueued, but hasn't yet started downloading") - case .downloading: - return NSLocalizedString("ATTACHMENT_DOWNLOADING_STATUS_IN_PROGRESS", comment: "Status label when an attachment is currently downloading") - case .failed: - return NSLocalizedString("ATTACHMENT_DOWNLOADING_STATUS_FAILED", comment: "Status label when an attachment download has failed.") - } - }() - - if attachmentPointer.state == .downloading { - progressView.isHidden = false - progressView.autoSetDimension(.height, toSize: 8) - } else { - progressView.isHidden = true - progressView.autoSetDimension(.height, toSize: 0) - } - } - - var textColor: UIColor { - return conversationStyle.bubbleTextColor(isIncoming: isIncoming) - } - - @objc - public class func measureHeight() -> CGFloat { - return ceil(nameFont().lineHeight + - statusFont().lineHeight + - progressHeight + - vSpacing * 2) - } -}