Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Voice master #2

Open
wants to merge 43 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
43 commits
Select commit Hold shift + click to select a range
9ccb264
Add voiceButton and change the inputBar UI
CCCCkgal May 14, 2018
c7a51e3
Change sendButton
CCCCkgal May 18, 2018
9ba002a
Change sendButton and voiceButton
CCCCkgal May 21, 2018
8554af6
Add voiceMessageCell and change voice ui
CCCCkgal May 24, 2018
c687e41
add voiceTimeLabel size to change loadingView UI
CCCCkgal May 25, 2018
22b54b8
add voicePlayView
CCCCkgal May 29, 2018
6308b18
download voice data
zhangcx627 May 30, 2018
b7796ad
Change loading view
CCCCkgal May 30, 2018
0c5f19a
Merge branch 'voice_Master' of https://github.com/agent8/MessageKit i…
CCCCkgal May 30, 2018
3f75cea
change voiceMessageCell width
CCCCkgal May 30, 2018
3e6d14d
changeVoiceplayed
zhangcx627 May 30, 2018
ad0e586
Merge branch 'voice_Master' of https://github.com/agent8/MessageKit i…
zhangcx627 May 30, 2018
9d6eae2
Revert "changeVoiceplayed"
zhangcx627 May 30, 2018
278e64e
VoicePlayed
zhangcx627 May 30, 2018
b51f88f
change red ball
CCCCkgal May 30, 2018
0a2f300
Merge branch 'voice_Master' of https://github.com/agent8/MessageKit i…
CCCCkgal May 30, 2018
3411cdf
loadingView
zhangcx627 May 31, 2018
3f46f69
Change NSLayoutConstraint about left and right voiceMessageCell
CCCCkgal May 31, 2018
6bb9ea7
Merge branch 'voice_Master' of https://github.com/agent8/MessageKit i…
CCCCkgal May 31, 2018
9992553
change about voiceMessageCell red ball
CCCCkgal May 31, 2018
95f9652
change the voiceTime
CCCCkgal Jun 1, 2018
19481ce
voice need add a bool in callback.
zhangcx627 Jun 1, 2018
77cb12b
Merge branch 'voice_Master' of https://github.com/agent8/MessageKit i…
zhangcx627 Jun 1, 2018
2c1b981
retry download
zhangcx627 Jun 1, 2018
0ddf48c
add download message error and retry
CCCCkgal Jun 4, 2018
9859de7
add voiceCell menu. reply a voice cell's width
zhangcx627 Jun 5, 2018
ffe43c0
Change download voice UI
CCCCkgal Jun 7, 2018
d23f7a1
download and refresh
zhangcx627 Jun 7, 2018
f3d039d
download voice again
CCCCkgal Jun 7, 2018
8584013
Change download voice
CCCCkgal Jun 7, 2018
9742761
max voice cell width
zhangcx627 Jun 12, 2018
8206f90
should continue animating when refresh.
zhangcx627 Jun 13, 2018
26b64bd
don't show 0″
zhangcx627 Jun 15, 2018
3e7c553
add some change about reply
CCCCkgal Jun 20, 2018
33f141b
Merge branch 'voice_Master' of https://github.com/agent8/MessageKit i…
CCCCkgal Jun 20, 2018
6b6dbca
if msg.mediaPath is not empty. should set downloadState as success
zhangcx627 Jun 21, 2018
2c34ee9
add messageContainerBaseView to do some about replyView UI
CCCCkgal Jun 21, 2018
891b4e0
Merge branch 'voice_Master' of https://github.com/agent8/MessageKit i…
CCCCkgal Jun 21, 2018
a2a373e
delete failed state
zhangcx627 Jun 27, 2018
88fc7d2
Merge branch 'master' into voice_Master
zhangcx627 Jun 27, 2018
6953898
miss commit
zhangcx627 Jun 27, 2018
c11bf0e
change some about Voice UI
CCCCkgal Jun 30, 2018
2eef641
download failed
zhangcx627 Jul 17, 2018
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions Sources/Controllers/MessagesViewController+DataSource.swift
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,11 @@ extension MessagesViewController: UICollectionViewDataSource {
messagesDataSource.configCell(cell, for: message, at: indexPath)
cell.configure(with: message, at: indexPath, and: messagesCollectionView)
return cell
case .audio(_):
let cell = messagesCollectionView.dequeueReusableCell(VoiceMessageCell.self, for: indexPath)
messagesDataSource.configCell(cell, for: message, at: indexPath)
cell.configure(with: message, at: indexPath, and: messagesCollectionView)
return cell
case .gif, .sticker:
let cell = messagesCollectionView.dequeueReusableCell(GifMessageCell.self, for: indexPath)
messagesDataSource.configCell(cell, for: message, at: indexPath)
Expand Down
2 changes: 1 addition & 1 deletion Sources/Controllers/MessagesViewController+Delegate.swift
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,7 @@ extension MessagesViewController: UICollectionViewDelegateFlowLayout {
let message = messagesDataSource.messageForItem(at: indexPath, in: messagesCollectionView)

switch message.data {
case .text, .attributedText, .emoji, .photo, .attachment, .gif, .sticker:
case .text, .attributedText, .emoji, .photo, .attachment, .audio, .gif, .sticker:
selectedIndexPathForMenu = indexPath
return true
default:
Expand Down
1 change: 1 addition & 0 deletions Sources/Controllers/MessagesViewController.swift
Original file line number Diff line number Diff line change
Expand Up @@ -150,6 +150,7 @@ open class MessagesViewController: UIViewController {
messagesCollectionView.register(LocationMessageCell.self)
messagesCollectionView.register(PhotoMessageCell.self)
messagesCollectionView.register(DocumentMessageCell.self)
messagesCollectionView.register(VoiceMessageCell.self)
messagesCollectionView.register(GifMessageCell.self)

messagesCollectionView.register(MessageFooterView.self, forSupplementaryViewOfKind: UICollectionElementKindSectionFooter)
Expand Down
22 changes: 22 additions & 0 deletions Sources/Extensions/UIView+Extensions.swift
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,28 @@ extension UIView {
]
NSLayoutConstraint.activate(constraints)
}
func rightInSuperview(_ rightConstant: CGFloat = 0) {
guard let superview = self.superview else {
return
}
translatesAutoresizingMaskIntoConstraints = false
let constraints: [NSLayoutConstraint] = [
rightAnchor.constraint(equalTo: superview.rightAnchor,constant: rightConstant),
centerYAnchor.constraint(equalTo: superview.centerYAnchor)
]
NSLayoutConstraint.activate(constraints)
}
func leftInSuperview(_ leftConstant: CGFloat = 0) {
guard let superview = self.superview else {
return
}
translatesAutoresizingMaskIntoConstraints = false
let constraints: [NSLayoutConstraint] = [
leftAnchor.constraint(equalTo: superview.leftAnchor,constant: leftConstant),
centerYAnchor.constraint(equalTo: superview.centerYAnchor)
]
NSLayoutConstraint.activate(constraints)
}

func constraint(equalTo size: CGSize) {
guard superview != nil else { return }
Expand Down
70 changes: 59 additions & 11 deletions Sources/Layout/MessageIntermediateLayoutAttributes.swift
Original file line number Diff line number Diff line change
Expand Up @@ -61,11 +61,11 @@ final class MessageIntermediateLayoutAttributes {
case .cellBottom:
origin.y = cellFrame.height - avatarSize.height
case .messageTop:
origin.y = messageContainerFrame.minY
origin.y = messageContainerBaseViewFrame.minY
case .messageBottom:
origin.y = messageContainerFrame.maxY - avatarSize.height
origin.y = messageContainerBaseViewFrame.maxY - avatarSize.height
case .messageCenter:
origin.y = messageContainerFrame.midY - (avatarSize.height/2)
origin.y = messageContainerBaseViewFrame.midY - (avatarSize.height/2)
}

return CGRect(origin: origin, size: avatarSize)
Expand All @@ -81,24 +81,50 @@ final class MessageIntermediateLayoutAttributes {
guard accessoryViewSize != .zero else { return .zero }

var origin: CGPoint = .zero
origin.y = messageContainerFrame.origin.y + messageContainerSize.height * 0.5 -
origin.y = messageContainerBaseViewFrame.origin.y + messageContainerSize.height * 0.5 -
accessoryViewSize.height * 0.5

switch avatarPosition.horizontal {
case .cellLeading:
origin.x = messageContainerFrame.maxX + accessoryViewPadding.left
origin.x = messageContainerBaseViewFrame.maxX + accessoryViewPadding.left + accessoryViewSize.width
case .cellTrailing:
origin.x = messageContainerFrame.minX - accessoryViewPadding.right - accessoryViewSize.width
origin.x = messageContainerBaseViewFrame.minX - accessoryViewPadding.right - accessoryViewSize.width - voiceTimeViewSize.width
case .natural:
fatalError(MessageKitError.avatarPositionUnresolved)
}

return CGRect(origin: origin, size: accessoryViewSize)

}()
// messageContainerBaseViewFrame
var messageContainerBaseViewSize: CGSize = .zero

var messageContainerBaseViewMaxWidth: CGFloat = 0
var messageContainerBaseViewPadding: UIEdgeInsets = .zero

lazy var messageContainerBaseViewFrame: CGRect = {

guard messageContainerBaseViewSize != .zero else { return .zero }

var origin: CGPoint = .zero
origin.y = topLabelSize.height + messageContainerBaseViewPadding.top + topLabelVerticalPadding

switch avatarPosition.horizontal {
case .cellLeading:
origin.x = avatarSize.width + messageContainerPadding.left
case .cellTrailing:
origin.x = cellFrame.width - avatarSize.width - messageContainerBaseViewSize.width - messageContainerBaseViewPadding.right
case .natural:
fatalError(MessageKitError.avatarPositionUnresolved)
}

return CGRect(origin: origin, size: messageContainerBaseViewSize)

}()

// MessageContainerView
var messageContainerSize: CGSize = .zero

var messageContainerMaxWidth: CGFloat = 0
var messageContainerPadding: UIEdgeInsets = .zero
var messageLabelInsets: UIEdgeInsets = .zero
Expand All @@ -123,6 +149,28 @@ final class MessageIntermediateLayoutAttributes {

}()

var voiceTimeViewSize: CGSize = .zero
var voiceTimeViewPadding: UIEdgeInsets = .zero
lazy var voiceTimeViewframe: CGRect = {

guard voiceTimeViewSize != .zero else { return .zero }

var origin: CGPoint = .zero
origin.y = messageContainerFrame.origin.y + messageContainerSize.height * 0.5 -
voiceTimeViewSize.height * 0.5

switch avatarPosition.horizontal {
case .cellLeading:
origin.x = messageContainerFrame.maxX + voiceTimeViewPadding.left
case .cellTrailing:
origin.x = messageContainerFrame.minX - voiceTimeViewPadding.right - voiceTimeViewSize.width
case .natural:
fatalError(MessageKitError.avatarPositionUnresolved)
}

return CGRect(origin: origin, size: voiceTimeViewSize)
}()

// Cell Top Label
var topLabelAlignment: LabelAlignment = .cellLeading(.zero)
var topLabelSize: CGSize = .zero
Expand All @@ -144,9 +192,9 @@ final class MessageIntermediateLayoutAttributes {
case .cellTrailing:
origin.x = cellFrame.width - topLabelSize.width - topLabelPadding.right
case .messageLeading:
origin.x = messageContainerFrame.minX + topLabelPadding.left
origin.x = messageContainerBaseViewFrame.minX + topLabelPadding.left
case .messageTrailing:
origin.x = messageContainerFrame.maxX - topLabelSize.width - topLabelPadding.right
origin.x = messageContainerBaseViewFrame.maxX - topLabelSize.width - topLabelPadding.right
}

return CGRect(origin: origin, size: topLabelSize)
Expand All @@ -164,7 +212,7 @@ final class MessageIntermediateLayoutAttributes {

var origin: CGPoint = .zero

origin.y = messageContainerFrame.maxY + messageContainerPadding.bottom + bottomLabelPadding.top
origin.y = messageContainerBaseViewFrame.maxY + messageContainerPadding.bottom + bottomLabelPadding.top

switch bottomLabelAlignment {
case .cellLeading:
Expand All @@ -174,9 +222,9 @@ final class MessageIntermediateLayoutAttributes {
case .cellTrailing:
origin.x = cellFrame.width - bottomLabelSize.width - bottomLabelPadding.right
case .messageLeading:
origin.x = messageContainerFrame.minX + bottomLabelPadding.left
origin.x = messageContainerBaseViewFrame.minX + bottomLabelPadding.left
case .messageTrailing:
origin.x = messageContainerFrame.maxX - bottomLabelSize.width - bottomLabelPadding.right
origin.x = messageContainerBaseViewFrame.maxX - bottomLabelSize.width - bottomLabelPadding.right
}

return CGRect(origin: origin, size: bottomLabelSize)
Expand Down
38 changes: 37 additions & 1 deletion Sources/Layout/MessagesCollectionViewFlowLayout.swift
Original file line number Diff line number Diff line change
Expand Up @@ -237,16 +237,27 @@ fileprivate extension MessagesCollectionViewFlowLayout {
attributes.avatarPosition = avatarPosition(for: attributes)
attributes.avatarSize = avatarSize(for: attributes)
attributes.messageContainerPadding = messageContainerPadding(for: attributes)

attributes.messageContainerBaseViewPadding = messageContainerPadding(for: attributes)

attributes.messageLabelInsets = messageLabelInsets(for: attributes)

// AccessoryView
attributes.accessoryViewSize = accessoryViewSize(for: attributes)
attributes.accessoryViewPadding = accessoryViewPadding(for: attributes)

// voiceTimeView
attributes.voiceTimeViewSize = voiceTimeViewSize(for: attributes)
attributes.voiceTimeViewPadding = voiceTimeViewPadding(for: attributes)

// MessageContainerView
attributes.messageContainerMaxWidth = messageContainerMaxWidth(for: attributes)
attributes.messageContainerSize = messageContainerSize(for: attributes)

// messageContainerBaseViewFrame
attributes.messageContainerBaseViewMaxWidth = messageContainerMaxWidth(for: attributes)
attributes.messageContainerBaseViewSize = messageContainerSize(for: attributes, voiceReplyWidth: 40)

// Cell Bottom Label
attributes.bottomLabelAlignment = cellBottomLabelAlignment(for: attributes)
attributes.bottomLabelMaxWidth = cellBottomLabelMaxWidth(for: attributes)
Expand Down Expand Up @@ -274,7 +285,9 @@ fileprivate extension MessagesCollectionViewFlowLayout {

intermediateAttributes.cellFrame = attributes.frame

attributes.messageContainerBaseViewFrame = intermediateAttributes.messageContainerBaseViewFrame
attributes.messageContainerFrame = intermediateAttributes.messageContainerFrame
attributes.voiceTimeViewframe = intermediateAttributes.voiceTimeViewframe
attributes.topLabelFrame = intermediateAttributes.topLabelFrame
attributes.bottomLabelFrame = intermediateAttributes.bottomLabelFrame
attributes.avatarFrame = intermediateAttributes.avatarFrame
Expand Down Expand Up @@ -409,6 +422,9 @@ private extension MessagesCollectionViewFlowLayout {
switch attributes.message.data {
case .text, .attributedText:
return baseMaxWidth - attributes.messageLabelHorizontalInsets
case .audio:
//czy: add voiceTimeLabel size
return baseMaxWidth - attributes.messageLabelHorizontalInsets
default:
return baseMaxWidth
}
Expand All @@ -420,7 +436,7 @@ private extension MessagesCollectionViewFlowLayout {
///
/// - Parameters:
/// - attributes: The `MessageIntermediateLayoutAttributes` to consider when calculating the `MessageContainerView` size.
func messageContainerSize(for attributes: MessageIntermediateLayoutAttributes) -> CGSize {
func messageContainerSize(for attributes: MessageIntermediateLayoutAttributes, voiceReplyWidth: CGFloat = 0) -> CGSize {

let message = attributes.message
let indexPath = attributes.indexPath
Expand Down Expand Up @@ -461,6 +477,16 @@ private extension MessagesCollectionViewFlowLayout {
let width = messagesLayoutDelegate.widthForLocation(message: message, at: indexPath, with: maxWidth, in: messagesCollectionView)
let height = messagesLayoutDelegate.heightForLocation(message: message, at: indexPath, with: maxWidth, in: messagesCollectionView)
messageContainerSize = CGSize(width: width, height: height)
case .audio(let data):

//计算宽度或者固定宽度
let minWidth: CGFloat = 60
let maxWidth: CGFloat = screenWidth() > 320 ? 240 : 200
let proportion:CGFloat = CGFloat(Double(data.duration)/60.0)
let width: CGFloat = minWidth + proportion * maxWidth * 2/5.0
let height: CGFloat = 35
messageContainerSize = CGSize(width: width, height: height)
messageContainerSize.width = max(messageContainerSize.width, replyWithLabelInsets) + voiceReplyWidth
}

messageContainerSize.height += messagesLayoutDelegate.replyViewHeight(at: indexPath,
Expand Down Expand Up @@ -641,6 +667,16 @@ fileprivate extension MessagesCollectionViewFlowLayout {
/// - attributes: The `MessageIntermediateLayoutAttributes` containing the `MessageType` object.
func accessoryViewPadding(for attributes: MessageIntermediateLayoutAttributes) -> UIEdgeInsets {
return messagesLayoutDelegate.accessoryViewPadding(for: attributes.message, at: attributes.indexPath, in: messagesCollectionView)

}

func voiceTimeViewSize(for attributes: MessageIntermediateLayoutAttributes) -> CGSize {
return messagesLayoutDelegate.voiceTimeViewSize(for: attributes.message, at: attributes.indexPath, in: messagesCollectionView)
}

func voiceTimeViewPadding(for attributes: MessageIntermediateLayoutAttributes) -> UIEdgeInsets {
return messagesLayoutDelegate.voiceTimeViewPadding(for: attributes.message, at: attributes.indexPath, in: messagesCollectionView)

}
}

Expand Down
4 changes: 4 additions & 0 deletions Sources/Layout/MessagesCollectionViewLayoutAttributes.swift
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,9 @@ final class MessagesCollectionViewLayoutAttributes: UICollectionViewLayoutAttrib
var accessoryViewFrame: CGRect = .zero

var messageLabelFont: UIFont = UIFont.preferredFont(forTextStyle: .body)
var messageContainerBaseViewFrame: CGRect = .zero
var messageContainerFrame: CGRect = .zero
var voiceTimeViewframe: CGRect = .zero
var messageLabelInsets: UIEdgeInsets = .zero

var topLabelFrame: CGRect = .zero
Expand All @@ -48,6 +50,8 @@ final class MessagesCollectionViewLayoutAttributes: UICollectionViewLayoutAttrib
copy.avatarFrame = avatarFrame
copy.accessoryViewFrame = accessoryViewFrame
copy.messageContainerFrame = messageContainerFrame
copy.messageContainerBaseViewFrame = messageContainerBaseViewFrame
copy.voiceTimeViewframe = voiceTimeViewframe
copy.messageLabelFont = messageLabelFont
copy.messageLabelInsets = messageLabelInsets
copy.topLabelFrame = topLabelFrame
Expand Down
5 changes: 4 additions & 1 deletion Sources/Models/MessageData.swift
Original file line number Diff line number Diff line change
Expand Up @@ -58,11 +58,12 @@ public enum MessageData {
/// An emoji message.
case emoji(String)


case attachment(data: ChatAttachment)

// MARK: - Not supported yet

// case audio(Data)
case audio(data: ChatAttachment)
//
// case system(String)
//
Expand All @@ -89,6 +90,8 @@ public enum MessageData {
return "Location"
case .emoji(_):
return "Emoji"
case .audio(_):
return "Voice"
case .attachment(let data):
if data.type == .Email {
return "Email"
Expand Down
11 changes: 11 additions & 0 deletions Sources/Protocols/MessagesLayoutDelegate.swift
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,8 @@ public protocol MessagesLayoutDelegate: AnyObject {
/// The default value returned by this method is zero.
func accessoryViewPadding(for message: MessageType, at indexPath: IndexPath, in messagesCollectionView: MessagesCollectionView) -> UIEdgeInsets

func voiceTimeViewPadding(for message: MessageType, at indexPath: IndexPath, in messagesCollectionView: MessagesCollectionView) -> UIEdgeInsets

/// Specifies the vertical and horizontal alignment for the `EdisonProfileView` in a `MessageCollectionViewCell`.
///
/// - Parameters:
Expand Down Expand Up @@ -114,6 +116,8 @@ public protocol MessagesLayoutDelegate: AnyObject {
/// The default value returned by this method is a size of `0 x 0`.
func accessoryViewSize(for message: MessageType, at indexPath: IndexPath, in messagesCollectionView: MessagesCollectionView) -> CGSize

func voiceTimeViewSize(for message: MessageType, at indexPath: IndexPath, in messagesCollectionView: MessagesCollectionView) -> CGSize

/// Specifies the size to use for a `MessageHeaderView`.
///
/// - Parameters:
Expand Down Expand Up @@ -242,6 +246,10 @@ public extension MessagesLayoutDelegate {
return .zero
}

func voiceTimeViewPadding(for message: MessageType, at indexPath: IndexPath, in messagesCollectionView: MessagesCollectionView) -> UIEdgeInsets {
return .zero
}

func cellTopLabelAlignment(for message: MessageType, at indexPath: IndexPath, in messagesCollectionView: MessagesCollectionView) -> LabelAlignment {
guard let dataSource = messagesCollectionView.messagesDataSource else {
fatalError(MessageKitError.nilMessagesDataSource)
Expand All @@ -267,6 +275,9 @@ public extension MessagesLayoutDelegate {
func accessoryViewSize(for message: MessageType, at indexPath: IndexPath, in messagesCollectionView: MessagesCollectionView) -> CGSize {
return .zero
}
func voiceTimeViewSize(for message: MessageType, at indexPath: IndexPath, in messagesCollectionView: MessagesCollectionView) -> CGSize {
return .zero
}

func headerViewSize(for message: MessageType, at indexPath: IndexPath, in messagesCollectionView: MessagesCollectionView) -> CGSize {
return .zero
Expand Down
2 changes: 1 addition & 1 deletion Sources/Views/Cells/DocumentMessageCell.swift
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ class DocumentMessageCell: MediaMessageCell {
let mailAcctId = chatAcct.mailAcctId

XMPPAdapter.downloadData(accountId: downloadInfo.accountId,
chatMsgId: downloadInfo.messageId) { (messageId, filePath) in
chatMsgId: downloadInfo.messageId) { (messageId, filePath, _) in
guard let path = filePath else {
return
}
Expand Down
2 changes: 1 addition & 1 deletion Sources/Views/Cells/GifMessageCell.swift
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ class GifMessageCell: MediaMessageCell {
}

XMPPAdapter.downloadData(accountId: downloadInfo.accountId,
chatMsgId: downloadInfo.messageId) { [weak self] (msgId, filePath) in
chatMsgId: downloadInfo.messageId) { [weak self] (msgId, filePath, _) in
EDOMainthread {
defer {
finishedAndDoNotRetry?(false)
Expand Down
1 change: 1 addition & 0 deletions Sources/Views/Cells/MediaMessageCell.swift
Original file line number Diff line number Diff line change
Expand Up @@ -108,6 +108,7 @@ open class MediaMessageCell: MessageCollectionViewCell {
downloadData(for: DownloadInfo(accountId: chatMsg.accountId, messageId: chatMsg.msgId))
}
}

case .gif(let downloadInfo), .sticker(let downloadInfo):
if let message: ChatMessage = EmailDAL.getChatMessage(accountId: downloadInfo.accountId,
msgId: downloadInfo.messageId),
Expand Down
Loading