Project Icon

Chat

SwiftUI聊天UI框架 自定义消息和内置媒体选择

Chat是一个基于SwiftUI的开源聊天UI框架,提供可自定义消息单元和内置媒体选择器。主要功能包括分页显示消息、发送新消息、自定义视图、多媒体选择和全屏消息菜单等。目前支持文本、照片、视频和音频消息,计划扩展到位置、文档和链接预览。框架设计灵活,支持多种聊天类型和回复模式,可用于开发各类聊天应用。

     

聊天媒体语音消息附加功能

聊天

一个SwiftUI聊天UI框架,具有完全可自定义的消息单元格和内置的媒体选择器

SPM Compatible Cocoapods Compatible Carthage Compatible License: MIT

功能

  • 显示您的消息并支持分页,允许您创建和"发送"新消息(发送意味着调用闭包,因为用户将提供实际的API调用)
  • 允许您为消息和输入视图传递自定义视图构建器
  • 内置照片和视频库/相机选择器,支持多媒体资产选择
  • 可以在长按消息单元格时显示全屏菜单(自动为长消息显示滚动)
  • 通过消息菜单或闭包支持"回复消息"。删除和编辑功能即将推出
  • 该库允许在消息中以任意组合发送以下内容:
    • 带/不带markdown的文本
    • 照片/视频
    • 音频录音 即将推出:
    • 用户位置
    • 文档
    • 带预览的链接

使用方法

像这样创建一个聊天视图:

@State var messages: [Message] = []

var body: some View {
    ChatView(messages: messages) { draft in
        yourViewModel.send(draft: draft)
    }
}

其中:
messages - 要显示的消息列表
didSendMessage - 用户按下发送按钮时调用的闭包

MessageChat用于内部实现的类型。在上面的代码中,它期望用户提供一个Message结构体列表,并在didSendMessage闭包中返回一个DraftMessage。您可以将其双向映射到您的API期望的自己的Message模型,或者按原样使用。

可用的聊天类型

聊天类型 - 决定消息的顺序和新消息动画的方向。可用选项:

  • conversation - 最新消息在底部,新消息从底部出现
  • comments - 最新消息在顶部,新消息从顶部出现

回复模式 - 决定回复消息的显示方式。可用选项:

  • quote - 当回复消息A时,新消息将作为最新消息出现,在其正文中引用消息A
  • answer - 当回复消息A时,新消息将直接出现在消息A下方作为单独的单元格,而不在其正文中重复消息A

要指定这些选项,可以通过init传递:

ChatView(messages: viewModel.messages, chatType: .comments, replyMode: .answer) { draft in
    yourViewModel.send(draft: draft)
}

自定义UI

您可以这样自定义消息单元格:

ChatView(messages: viewModel.messages) { draft in
    viewModel.send(draft: draft)
} messageBuilder: { message, positionInUserGroup, positionInCommentsGroup, showContextMenuClosure, messageActionClosure, showAttachmentClosure in
    VStack {
        Text(message.text)
        if !message.attachments.isEmpty {
            ForEach(message.attachments, id: \.id) { at in
                AsyncImage(url: at.thumbnail)
            }
        }
    }
}

messageBuilder的参数:

  • message - 包含用户信息、附件等的消息
  • positionInUserGroup - 消息在同一用户连续消息集合中的位置
  • positionInCommentsGroup - 消息在其连续评论组中的位置(仅适用于.answer回复模式,.quote模式下为nil)
  • showContextMenuClosure - 显示消息上下文菜单的闭包
  • messageActionClosure - 传递用户交互的闭包,例如.reply
  • showAttachmentClosure - 您可以将附件传递给此闭包以使用ChatView的全屏媒体查看器

您可以这样自定义输入视图(底部带按钮的文本字段):

ChatView(messages: viewModel.messages) { draft in
    viewModel.send(draft: draft)
} inputViewBuilder: { textBinding, attachments, inputViewState, inputViewStyle, inputViewActionClosure, dismissKeyboardClosure in
    Group {
        switch inputViewStyle {
        case .message: // 聊天屏幕上的输入视图
            VStack {
                HStack {
                    Button("发送") { inputViewActionClosure(.send) }
                    Button("附加") { inputViewActionClosure(.photo) }
                }
                TextField("输入您的消息", text: textBinding)
            }
        case .signature: // 照片选择屏幕上的输入视图
            VStack {
                HStack {
                    Button("发送") { inputViewActionClosure(.send) }
                }
                TextField("为照片添加说明", text: textBinding)
                    .background(Color.green)
            }
        }
    }
}

inputViewBuilder的参数:

  • textBinding 用于绑定您自己的TextField
  • attachments 是一个包含照片、视频、录音和您正在回复的消息的结构体
  • inputViewState - 输入视图的状态,如果可能,由库自动控制,或通过您调用inputViewActionClosure来控制
  • inputViewStyle - .message.signature(聊天屏幕或照片选择屏幕)
  • inputViewActionClosure 用于在点击您的自定义按钮时调用。例如,如果您想用自己的按钮发送消息,可以调用inputViewActionClosure(.send),然后库会重置文本和附件并调用didSendMessage发送闭包
  • dismissKeyboardClosure - 调用此闭包以关闭键盘

自定义消息菜单

长按消息将显示该消息的菜单(可以关闭,请参见修饰符)。要定义自定义消息菜单操作,请声明一个符合MessageMenuAction的枚举。然后,如果您将枚举的名称传递给它,库将在长按消息时显示您的自定义菜单选项,而不是默认选项(请参见代码示例)。一旦选择了操作,将调用特殊回调。这里是一个简单的例子:

enum Action: MessageMenuAction {
    case reply, edit

    func title() -> String {
        switch self {
        case .reply:
            "回复"
        case .edit:
            "编辑"
        }
    }
    
    func icon() -> Image {
        switch self {
        case .reply:
            Image(systemName: "arrowshape.turn.up.left")
        case .edit:
            Image(systemName: "square.and.pencil")
        }
    }
}
ChatView(messages: viewModel.messages) { draft in
    viewModel.send(draft: draft)
} messageMenuAction: { (action: Action, defaultActionClosure, message) in // <-- 在这里:指定你的 `MessageMenuAction` 枚举的名称
    switch action {
    case .reply:
        defaultActionClosure(message, .reply)
    case .edit:
        defaultActionClosure(message, .edit { editedText in
            // 在你的后端更新这条消息的文本
            print(editedText)
        })
    }
}

messageMenuAction 的参数:

  • selectedMenuAction - 用户从菜单中选择的操作。注意:声明这个变量时,需要明确指定其类型(你自定义的 MessageMenuAction 的子类)
  • defaultActionClosure - 一个闭包,接受 MessageMenuAction 默认实现的案例,提供简单的操作处理器;如果你需要默认操作,可以调用这个闭包,传入选中的消息并选择一个默认操作(.reply, .edit);或者你可以为所有操作编写自定义实现,在这种情况下只需忽略这个闭包
  • message - 显示菜单的消息

在实现你自己的 MessageMenuActionClosure 时,编写一个 switch 语句遍历你的 MessageMenuAction 的所有情况,在每个 case 中编写你自己的操作处理器,或者调用默认的处理器。注意:并非所有默认操作都能开箱即用 - 例如,对于 .edit,你仍需提供一个闭包来在后端保存编辑后的文本。请参考 ChatExample 项目中的 CommentsExampleView 以了解 MessageMenuActionClosure 的使用示例。

小型视图构建器:

这些使用 AnyView,所以请尽量保持简单

  • betweenListAndInputViewBuilder - 在聊天列表视图和输入视图之间显示的内容
  • mainHeaderBuilder - 整个聊天的头部,会随所有消息和头部一起滚动
  • headerBuilder - 日期分节头部构建器

修饰符

isListAboveInputView - 消息表格是否在输入字段视图上方 showDateHeaders - 是否在不同日期之间显示带日期的分节头部,默认为 true isScrollEnabled - 禁止消息 UITableView 的滚动 showMessageMenuOnLongPress - 开启/关闭长按显示菜单 showNetworkConnectionProblem - 开启/关闭网络错误显示 assetsPickerLimit - 设置库内置 MediaPicker 的限制 setMediaPickerSelectionParameters - 一个结构体,持有 MediaPicker 的选择参数(assetsPickerLimit 和其他如 mediaType, selectionStyle 等) orientationHandler - 处理屏幕旋转

enableLoadMore(offset: Int, handler: @escaping ChatPaginationClosure) - 当用户滚动到距离末尾第 offset 条消息时,调用处理函数,以便用户加载更多消息 chatNavigation(title: String, status: String? = nil, cover: URL? = nil) - 传递聊天导航栏的信息

仅适用于内置消息视图

avatarSize - 默认头像是一个圆形,你可以在这里指定其直径 tapAvatarClosure - 点击头像时调用的闭包 messageUseMarkdown - 是否使用 markdown(例如用 ** 使文字加粗) showMessageTimeView - 在消息角落显示时间戳 setMessageFont - 传递自定义字体用于消息

仅适用于内置输入视图

setAvailableInput - 在默认 InputView 中隐藏一些按钮。可用选项有: - .full - 媒体 + 文本 + 音频 - .textAndMedia - .textAndAudio - .textOnly

示例

有两个示例项目:

  • 一个是简单的机器人,每2秒发送随机文本/媒体消息。它没有后端和本地存储。每次启动都是全新的。
  • 另一个与 Firestore 数据库集成。它具有所有必要的后端支持,包括存储媒体和音频消息、未读消息计数器等。你需要创建自己的 Firestore 应用和数据库。还需用你自己的替换 GoogleService-Info。之后你可以在多个模拟器/设备上进行测试。

创建你的 firestore 应用 https://console.firebase.google.com/ 创建 firesote 数据库(用于轻量级文本数据) https://firebase.google.com/docs/firestore/manage-data/add-data 创建云 firestore 数据库(用于图片和语音录音) https://firebase.google.com/docs/storage/web/start

示例

要尝试 Chat 示例:

  • 克隆仓库 git clone git@github.com:exyte/Chat.git
  • 打开终端并运行 cd <ChatRepo>/Example
  • 等待 SPM 下载完成包
  • 运行它!

安装

Swift Package Manager

dependencies: [
    .package(url: "https://github.com/exyte/Chat.git")
]

CocoaPods

pod 'ExyteChat'

Carthage

github "Exyte/Chat"

要求

  • iOS 16+
  • Xcode 14+

我们的其他开源 SwiftUI 库

PopupView - 吐司和弹出窗口库 Grid - 最强大的网格容器 ScalingHeaderScrollView - 带有随滚动缩小的粘性头部的滚动视图 AnimatedTabBar - 带有多种预设动画的标签栏 MediaPicker - 可自定义的媒体选择器 OpenAI OpenAI REST API 的包装库 AnimatedGradient - 动画线性渐变 ConcentricOnboarding - 动画引导流程 FloatingButton - 浮动按钮菜单 ActivityIndicatorView - 多种动画加载指示器 ProgressIndicatorView - 多种动画进度指示器 FlagAndCountryCode - 每个国家的电话区号和国旗 SVGView - SVG 解析器 LiquidSwipe - 液体导航动画

项目侧边栏1项目侧边栏2
推荐项目
Project Cover

豆包MarsCode

豆包 MarsCode 是一款革命性的编程助手,通过AI技术提供代码补全、单测生成、代码解释和智能问答等功能,支持100+编程语言,与主流编辑器无缝集成,显著提升开发效率和代码质量。

Project Cover

AI写歌

Suno AI是一个革命性的AI音乐创作平台,能在短短30秒内帮助用户创作出一首完整的歌曲。无论是寻找创作灵感还是需要快速制作音乐,Suno AI都是音乐爱好者和专业人士的理想选择。

Project Cover

有言AI

有言平台提供一站式AIGC视频创作解决方案,通过智能技术简化视频制作流程。无论是企业宣传还是个人分享,有言都能帮助用户快速、轻松地制作出专业级别的视频内容。

Project Cover

Kimi

Kimi AI助手提供多语言对话支持,能够阅读和理解用户上传的文件内容,解析网页信息,并结合搜索结果为用户提供详尽的答案。无论是日常咨询还是专业问题,Kimi都能以友好、专业的方式提供帮助。

Project Cover

阿里绘蛙

绘蛙是阿里巴巴集团推出的革命性AI电商营销平台。利用尖端人工智能技术,为商家提供一键生成商品图和营销文案的服务,显著提升内容创作效率和营销效果。适用于淘宝、天猫等电商平台,让商品第一时间被种草。

Project Cover

吐司

探索Tensor.Art平台的独特AI模型,免费访问各种图像生成与AI训练工具,从Stable Diffusion等基础模型开始,轻松实现创新图像生成。体验前沿的AI技术,推动个人和企业的创新发展。

Project Cover

SubCat字幕猫

SubCat字幕猫APP是一款创新的视频播放器,它将改变您观看视频的方式!SubCat结合了先进的人工智能技术,为您提供即时视频字幕翻译,无论是本地视频还是网络流媒体,让您轻松享受各种语言的内容。

Project Cover

美间AI

美间AI创意设计平台,利用前沿AI技术,为设计师和营销人员提供一站式设计解决方案。从智能海报到3D效果图,再到文案生成,美间让创意设计更简单、更高效。

Project Cover

稿定AI

稿定设计 是一个多功能的在线设计和创意平台,提供广泛的设计工具和资源,以满足不同用户的需求。从专业的图形设计师到普通用户,无论是进行图片处理、智能抠图、H5页面制作还是视频剪辑,稿定设计都能提供简单、高效的解决方案。该平台以其用户友好的界面和强大的功能集合,帮助用户轻松实现创意设计。

投诉举报邮箱: service@vectorlightyear.com
@2024 懂AI·鲁ICP备2024100362号-6·鲁公网安备37021002001498号