Implement conversation screen subtitle
This commit is contained in:
parent
f12d18f90e
commit
ac41400ede
|
@ -563,6 +563,7 @@
|
|||
C3645350252449260045C478 /* VoiceMessageView.swift in Sources */ = {isa = PBXBuildFile; fileRef = C364534F252449260045C478 /* VoiceMessageView.swift */; };
|
||||
C364535C252467900045C478 /* AudioUtilities.swift in Sources */ = {isa = PBXBuildFile; fileRef = C364535B252467900045C478 /* AudioUtilities.swift */; };
|
||||
C374EEE225DA26740073A857 /* LinkPreviewModal.swift in Sources */ = {isa = PBXBuildFile; fileRef = C374EEE125DA26740073A857 /* LinkPreviewModal.swift */; };
|
||||
C374EEEB25DA3CA70073A857 /* ConversationTitleViewV2.swift in Sources */ = {isa = PBXBuildFile; fileRef = C374EEEA25DA3CA70073A857 /* ConversationTitleViewV2.swift */; };
|
||||
C379DCF4256735770002D4EB /* VisibleMessage+Attachment.swift in Sources */ = {isa = PBXBuildFile; fileRef = C379DCF3256735770002D4EB /* VisibleMessage+Attachment.swift */; };
|
||||
C37F5385255B94F6002AEA92 /* SelectRecipientViewController.h in Headers */ = {isa = PBXBuildFile; fileRef = C38EF34E255B6DC8007E1867 /* SelectRecipientViewController.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
C37F5396255B95BD002AEA92 /* OWSAnyTouchGestureRecognizer.h in Headers */ = {isa = PBXBuildFile; fileRef = C38EF302255B6DBE007E1867 /* OWSAnyTouchGestureRecognizer.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
|
@ -1606,6 +1607,7 @@
|
|||
C364534F252449260045C478 /* VoiceMessageView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = VoiceMessageView.swift; sourceTree = "<group>"; };
|
||||
C364535B252467900045C478 /* AudioUtilities.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AudioUtilities.swift; sourceTree = "<group>"; };
|
||||
C374EEE125DA26740073A857 /* LinkPreviewModal.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LinkPreviewModal.swift; sourceTree = "<group>"; };
|
||||
C374EEEA25DA3CA70073A857 /* ConversationTitleViewV2.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ConversationTitleViewV2.swift; sourceTree = "<group>"; };
|
||||
C379DCF3256735770002D4EB /* VisibleMessage+Attachment.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "VisibleMessage+Attachment.swift"; sourceTree = "<group>"; };
|
||||
C379DCFD25673DBC0002D4EB /* TSAttachmentPointer+Conversion.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "TSAttachmentPointer+Conversion.swift"; sourceTree = "<group>"; };
|
||||
C37F53E8255BA9BB002AEA92 /* Environment.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = Environment.h; sourceTree = "<group>"; };
|
||||
|
@ -2251,6 +2253,7 @@
|
|||
C374EEE125DA26740073A857 /* LinkPreviewModal.swift */,
|
||||
B82149C025D605C6009C0F2A /* InfoBanner.swift */,
|
||||
B8214A2A25D63EB9009C0F2A /* MessagesTableView.swift */,
|
||||
C374EEEA25DA3CA70073A857 /* ConversationTitleViewV2.swift */,
|
||||
);
|
||||
path = "Views & Modals";
|
||||
sourceTree = "<group>";
|
||||
|
@ -5056,6 +5059,7 @@
|
|||
B8214A2B25D63EB9009C0F2A /* MessagesTableView.swift in Sources */,
|
||||
B835246E25C38ABF0089A44F /* ConversationVC.swift in Sources */,
|
||||
B821494625D4D6FF009C0F2A /* URLModal.swift in Sources */,
|
||||
C374EEEB25DA3CA70073A857 /* ConversationTitleViewV2.swift in Sources */,
|
||||
4CA485BB2232339F004B9E7D /* PhotoCaptureViewController.swift in Sources */,
|
||||
34330AA31E79686200DF2FB9 /* OWSProgressView.m in Sources */,
|
||||
344825C6211390C800DB4BD8 /* OWSOrphanDataCleaner.m in Sources */,
|
||||
|
|
|
@ -3,7 +3,6 @@
|
|||
// • Tapping replies
|
||||
// • Mentions
|
||||
// • Remaining send logic
|
||||
// • Subtitle
|
||||
// • Slight paging glitch
|
||||
// • Scrolling bug
|
||||
// • Scroll button bug
|
||||
|
@ -47,6 +46,8 @@ final class ConversationVC : BaseVC, ConversationViewModelDelegate, UITableViewD
|
|||
}()
|
||||
|
||||
// MARK: UI Components
|
||||
private lazy var titleView = ConversationTitleViewV2(thread: thread)
|
||||
|
||||
lazy var messagesTableView: MessagesTableView = {
|
||||
let result = MessagesTableView()
|
||||
result.dataSource = self
|
||||
|
@ -98,7 +99,7 @@ final class ConversationVC : BaseVC, ConversationViewModelDelegate, UITableViewD
|
|||
setUpGradientBackground()
|
||||
// Nav bar
|
||||
setUpNavBarStyle()
|
||||
setNavBarTitle(getTitle())
|
||||
navigationItem.titleView = titleView
|
||||
updateNavBarButtons()
|
||||
// Constraints
|
||||
view.addSubview(messagesTableView)
|
||||
|
@ -390,21 +391,6 @@ final class ConversationVC : BaseVC, ConversationViewModelDelegate, UITableViewD
|
|||
}
|
||||
|
||||
// MARK: Convenience
|
||||
private func getTitle() -> String {
|
||||
if let thread = thread as? TSGroupThread {
|
||||
return thread.groupModel.groupName!
|
||||
} else if thread.isNoteToSelf() {
|
||||
return "Note to Self"
|
||||
} else {
|
||||
let sessionID = thread.contactIdentifier()!
|
||||
var result = sessionID
|
||||
Storage.read { transaction in
|
||||
result = Storage.shared.getContact(with: sessionID)?.displayName ?? "Anonymous"
|
||||
}
|
||||
return result
|
||||
}
|
||||
}
|
||||
|
||||
private func getScrollButtonOpacity() -> CGFloat {
|
||||
let contentOffsetY = messagesTableView.contentOffset.y
|
||||
let x = (lastPageTop - ConversationVC.bottomInset - contentOffsetY).clamp(0, .greatestFiniteMagnitude)
|
||||
|
|
|
@ -0,0 +1,109 @@
|
|||
|
||||
final class ConversationTitleViewV2 : UIView {
|
||||
private let thread: TSThread
|
||||
|
||||
override var intrinsicContentSize: CGSize {
|
||||
return UIView.layoutFittingExpandedSize
|
||||
}
|
||||
|
||||
// MARK: UI Components
|
||||
private lazy var titleLabel: UILabel = {
|
||||
let result = UILabel()
|
||||
result.textColor = Colors.text
|
||||
result.font = .boldSystemFont(ofSize: Values.mediumFontSize)
|
||||
result.lineBreakMode = .byTruncatingTail
|
||||
return result
|
||||
}()
|
||||
|
||||
private lazy var subtitleLabel: UILabel = {
|
||||
let result = UILabel()
|
||||
result.textColor = Colors.text
|
||||
result.font = .systemFont(ofSize: 13)
|
||||
result.lineBreakMode = .byTruncatingTail
|
||||
return result
|
||||
}()
|
||||
|
||||
// MARK: Lifecycle
|
||||
init(thread: TSThread) {
|
||||
self.thread = thread
|
||||
super.init(frame: CGRect.zero)
|
||||
initialize()
|
||||
}
|
||||
|
||||
override init(frame: CGRect) {
|
||||
preconditionFailure("Use init(thread:) instead.")
|
||||
}
|
||||
|
||||
required init?(coder: NSCoder) {
|
||||
preconditionFailure("Use init(coder:) instead.")
|
||||
}
|
||||
|
||||
private func initialize() {
|
||||
let stackView = UIStackView(arrangedSubviews: [ titleLabel, subtitleLabel ])
|
||||
stackView.axis = .vertical
|
||||
stackView.alignment = .center
|
||||
stackView.isLayoutMarginsRelativeArrangement = true
|
||||
stackView.layoutMargins = UIEdgeInsets(top: 0, left: 8, bottom: 0, right: 0)
|
||||
addSubview(stackView)
|
||||
stackView.pin(to: self)
|
||||
NotificationCenter.default.addObserver(self, selector: #selector(update), name: Notification.Name.groupThreadUpdated, object: nil)
|
||||
NotificationCenter.default.addObserver(self, selector: #selector(update), name: Notification.Name.muteSettingUpdated, object: nil)
|
||||
update()
|
||||
}
|
||||
|
||||
deinit {
|
||||
NotificationCenter.default.removeObserver(self)
|
||||
}
|
||||
|
||||
// MARK: Updating
|
||||
@objc private func update() {
|
||||
titleLabel.text = getTitle()
|
||||
let subtitle = getSubtitle()
|
||||
subtitleLabel.attributedText = subtitle
|
||||
let titleFontSize = (subtitle != nil) ? Values.mediumFontSize : Values.veryLargeFontSize
|
||||
titleLabel.font = .boldSystemFont(ofSize: titleFontSize)
|
||||
}
|
||||
|
||||
// MARK: General
|
||||
private func getTitle() -> String {
|
||||
if let thread = thread as? TSGroupThread {
|
||||
return thread.groupModel.groupName!
|
||||
} else if thread.isNoteToSelf() {
|
||||
return "Note to Self"
|
||||
} else {
|
||||
let sessionID = thread.contactIdentifier()!
|
||||
var result = sessionID
|
||||
Storage.read { transaction in
|
||||
result = Storage.shared.getContact(with: sessionID)?.displayName ?? "Anonymous"
|
||||
}
|
||||
return result
|
||||
}
|
||||
}
|
||||
|
||||
private func getSubtitle() -> NSAttributedString? {
|
||||
if let muteEndDate = thread.mutedUntilDate, thread.isMuted {
|
||||
let result = NSMutableAttributedString()
|
||||
result.append(NSAttributedString(string: "\u{e067} ", attributes: [ .font : UIFont.ows_elegantIconsFont(10), .foregroundColor : Colors.text ]))
|
||||
let formatter = DateFormatter()
|
||||
formatter.locale = Locale.current
|
||||
formatter.timeStyle = .medium
|
||||
formatter.dateStyle = .medium
|
||||
result.append(NSAttributedString(string: "Muted until " + formatter.string(from: muteEndDate)))
|
||||
return result
|
||||
} else if let thread = self.thread as? TSGroupThread {
|
||||
var userCount: Int?
|
||||
switch thread.groupModel.groupType {
|
||||
case .closedGroup: userCount = thread.groupModel.groupMemberIds.count
|
||||
case .openGroup:
|
||||
if let openGroup = Storage.shared.getOpenGroup(for: self.thread.uniqueId!) {
|
||||
userCount = Storage.shared.getUserCount(forOpenGroupWithID: openGroup.id)
|
||||
}
|
||||
default: break
|
||||
}
|
||||
if let userCount = userCount {
|
||||
return NSAttributedString(string: "\(userCount) members")
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
}
|
|
@ -2,9 +2,11 @@
|
|||
public extension Notification.Name {
|
||||
|
||||
static let groupThreadUpdated = Notification.Name("groupThreadUpdated")
|
||||
static let muteSettingUpdated = Notification.Name("muteSettingUpdated")
|
||||
}
|
||||
|
||||
@objc public extension NSNotification {
|
||||
|
||||
@objc static let groupThreadUpdated = Notification.Name.groupThreadUpdated.rawValue as NSString
|
||||
@objc static let muteSettingUpdated = Notification.Name.muteSettingUpdated.rawValue as NSString
|
||||
}
|
||||
|
|
|
@ -451,6 +451,10 @@ BOOL IsNoteToSelfEnabled(void)
|
|||
changeBlock:^(TSThread *thread) {
|
||||
[thread setMutedUntilDate:mutedUntilDate];
|
||||
}];
|
||||
|
||||
[transaction addCompletionQueue:dispatch_get_main_queue() completionBlock:^{
|
||||
[NSNotificationCenter.defaultCenter postNotificationName:NSNotification.muteSettingUpdated object:self.uniqueId];
|
||||
}];
|
||||
}
|
||||
|
||||
@end
|
||||
|
|
Loading…
Reference in New Issue