diff --git a/Signal/src/ViewControllers/HomeViewController.m b/Signal/src/ViewControllers/HomeViewController.m index 344c90819..0c4af11c7 100644 --- a/Signal/src/ViewControllers/HomeViewController.m +++ b/Signal/src/ViewControllers/HomeViewController.m @@ -284,6 +284,15 @@ typedef NS_ENUM(NSInteger, CellState) { kArchiveState, kInboxState }; } [self updateBarButtonItems]; + + dispatch_async(dispatch_get_main_queue(), ^{ + NSIndexPath *indexPath = [NSIndexPath indexPathForRow:0 inSection:0]; + TSThread *thread = [self threadForIndexPath:indexPath]; + if (!thread) { + return; + } + [self presentThread:thread keyboardOnViewAppearing:NO callOnViewAppearing:NO]; + }); } - (void)viewDidAppear:(BOOL)animated diff --git a/SignalServiceKit/src/Messages/OWSMessageUtils.m b/SignalServiceKit/src/Messages/OWSMessageUtils.m index db91ddeb6..3c7e93fdb 100644 --- a/SignalServiceKit/src/Messages/OWSMessageUtils.m +++ b/SignalServiceKit/src/Messages/OWSMessageUtils.m @@ -4,6 +4,8 @@ #import "OWSMessageUtils.h" #import "AppContext.h" +#import "MIMETypeUtil.h" +#import "OWSMessageSender.h" #import "OWSPrimaryStorage.h" #import "TSAccountManager.h" #import "TSAttachment.h" @@ -136,8 +138,8 @@ NS_ASSUME_NONNULL_BEGIN OWSAssert(transaction); uint64_t timestamp = message.timestamp; - NSString *_Nullable body = message.body; - BOOL hasText = body.length > 0; + NSString *_Nullable quotedText = message.body; + BOOL hasText = quotedText.length > 0; BOOL hasAttachment = NO; NSString *_Nullable sourceFilename = nil; NSData *_Nullable thumbnailData = nil; @@ -148,11 +150,46 @@ NS_ASSUME_NONNULL_BEGIN TSAttachment *_Nullable attachment = [TSAttachment fetchObjectWithUniqueID:attachmentId transaction:transaction]; if (attachment) { - sourceFilename = attachment.sourceFilename; - contentType = attachment.contentType; - // Try to generate a thumbnail, if possible. - thumbnailData = [self thumbnailDataForAttachment:attachment]; - hasAttachment = YES; + // If the attachment is "oversize text", try to treat it appropriately. + if (!hasText && [NSObject isNullableObject:attachment.contentType equalTo:OWSMimeTypeOversizeTextMessage] && + [attachment isKindOfClass:[TSAttachmentStream class]]) { + + hasText = YES; + quotedText = @""; + + TSAttachmentStream *attachmentStream = (TSAttachmentStream *)attachment; + NSData *_Nullable oversizeTextData = [NSData dataWithContentsOfFile:attachmentStream.filePath]; + if (oversizeTextData) { + NSString *_Nullable oversizeText = + [[NSString alloc] initWithData:oversizeTextData encoding:NSUTF8StringEncoding]; + // First, truncate to the rough max characters. + NSString *_Nullable truncatedText = + [oversizeText substringToIndex:kOversizeTextMessageSizeThreshold - 1]; + // But kOversizeTextMessageSizeThreshold is in _bytes_, not characters, + // so we need to continue to trim the string until it fits. + while (truncatedText && truncatedText.length > 0 && + [truncatedText dataUsingEncoding:NSUTF8StringEncoding].length + >= kOversizeTextMessageSizeThreshold) { + // A very coarse binomial search by halving is acceptable, since + // kOversizeTextMessageSizeThreshold is much longer than our target + // length of "three short lines of text on any device we might + // display this on. + // + // We don't worry much about the search converging because + truncatedText = [truncatedText substringToIndex:oversizeText.length / 2]; + } + if ([truncatedText dataUsingEncoding:NSUTF8StringEncoding].length + < kOversizeTextMessageSizeThreshold) { + quotedText = truncatedText; + } + } + } else { + sourceFilename = attachment.sourceFilename; + contentType = attachment.contentType; + // Try to generate a thumbnail, if possible. + thumbnailData = [self thumbnailDataForAttachment:attachment]; + hasAttachment = YES; + } } } @@ -161,9 +198,11 @@ NS_ASSUME_NONNULL_BEGIN return nil; } + // It's conceivable that the logic above will find neither valid text + // or an attachment to quote. TSQuotedMessage *quotedMessage = [[TSQuotedMessage alloc] initWithTimestamp:timestamp authorId:authorId - body:body + body:quotedText sourceFilename:sourceFilename thumbnailData:thumbnailData contentType:contentType];