agora-chat-uikit
is a UI component library based on the Chat SDK. It provides pure UI components, module components containing chat business logic, and container components, which allow users to customize using renderX method. agora-chat-uikit
provides a provider to manage data. The provider automatically listens for chat SDK events to update data and drive UI updates. Developers can use the library to quickly build custom IM applications based on actual business requirements.
UIKIt consists of three parts: UI component, mobx store for managing data, and chat SDK. UI components include container components, composite components module, and pure UI components. These components at different levels are currently available to you. You can reference any of these components to build your own applications. UIkit uses mobx to manage global data, and you can reference the rootStore to get all the data and the action method which can be used to modify the data. UIKit integrates the chat SDK internally and interacts with the server through the chat SDK.
The agora-chat-uikit
library provides the following functions:
- Automatic layout to match the width and height of the container.
- Send and receive messages, display messages, show the message unread count, clear messages, and support message types (including text, image, file, emoji, voice, video, combined message, and contact card message).
- Search for and delete a conversation and pin a conversation.
- Contacts list.
- Customize the UI.
Module | Function | Description |
Conversation List | ||
Display conversation information | Displays information such as avatars, nicknames, last message, and unread message count of the conversation | |
Delete conversation | Deletes the conversation from the conversation list | |
Pin conversation | Pins the conversation | |
Mute conversation | Mutes the conversation from the conversation list | |
Chat | ||
Message input | Support for sending text, emoji, image, file, voice, and video messages | |
Display message | Displaying one-to-one or group chat messages, including the profile avatar, nickname, message content, time, message sending status, and message read status. Supported message types include text, image, video, file, voice, and combined messages, as well as contact card messages | |
Operate on messages | Including forwarding, editing, deleting, replying to, recalling, translating, and selecting messages, as well as operations on message Reactions and threads | |
Contacts | ||
Display groups and contacts | Display groups contacts and new requests | |
Display groups and contacts details | Display detailed information about groups or contacts, including avatars, nicknames, IDs, presence, and the ability to initiate messaging and audio/video calls |
In order to follow the procedure in this page, you must have:
- React 16.8.0 or later
- React DOM 16.8.0 or later
- A valid Agora account
- A valid Agora project with an App Key
Browser | Supported Version |
---|---|
IE | 11 or later |
Edge | 43 or later |
Firefox | 10 or later |
Chrome | 54 or later |
Safari | 11 or later |
URL Preview Limitations:If a website does not have cross-origin resource sharing (CORS) configured, it may lead to issues with URL resolution. CORS is a security mechanism that restricts cross-origin requests initiated from a web browser. When a cross-origin request is made from a web page using JavaScript or other client-side technologies, the browser sends a preflight request (OPTIONS request) to confirm whether the target server allows the cross-origin request. If the target server is not properly configured for CORS, the browser rejects the cross-origin request, resulting in the inability to access and resolve the URL. It's important to note that CORS restrictions are enforced by the browser as a security policy, and they only apply to cross-origin requests initiated from the client-side. If URL resolution is performed on the server-side, it usually won't be subject to CORS limitations. In such cases, URL resolution can be directly performed on the server-side without the need for client-side scripting to initiate the request.
# Install a CLI tool.
npm install create-react-app
# Create an my-app project.
npx create-react-app my-app
cd my-app
The project directory:
├── package.json
├── public # The static directory of Webpack.
│ ├── favicon.ico
│ ├── index.html # The default single-page app.
│ └── manifest.json
├── src
│ ├── App.css # The CSS of the app's root component.
│ ├── App.js # The app component code.
│ ├── App.test.js
│ ├── index.css # The style of the startup file.
│ ├── index.js # The startup file.
│ ├── logo.svg
│ └── serviceWorker.js
└── yarn.lock
- To install the Web Chat UIKit with npm, run the following command:
npm install agora-chat-uikit --save
- To Install the Web Chat UIKit with Yarn, run the following command:
yarn add agora-chat-uikit
Import agora-chat-uikit into your code.
// App.js
import React, { Component, useEffect } from 'react';
import { UIKitProvider, Chat, ConversationList, useClient, rootStore } from 'agora-chat-uikit';
import 'agora-chat-uikit/style.css';
const appKey = 'you app key'; // your appKey
const user = ''; // your user ID
const accessToken = ''; // agora chat token
const conversation = {
chatType: 'singleChat', // 'singleChat' || 'groupChat'
conversationId: 'agora', // target user ID or group ID
name: 'Agora', // target user nickname or group name
lastMessage: {},
};
const ChatApp = () => {
const client = useClient();
useEffect(() => {
client &&
client
.open({
user,
accessToken,
})
.then(res => {
console.log('get token success', res);
// create a conversation
rootStore.conversationStore.addConversation(conversation);
});
}, [client]);
return (
<div>
<div>
<ConversationList />
</div>
<div>
<Chat />
</div>
</div>
);
};
class App extends Component {
render() {
return (
<UIKitProvider
initConfig={{
appKey,
}}
>
<ChatApp />
</UIKitProvider>
);
}
}
export default App;
npm run start
Now, you can see your app in the browser.
For quick experience, you can use the default App Key and send several types of messages. Specifically, you can select a contact, enter your first message, and send it.
Note
If a custom App Key is used, no contact is available by default and you need to first add contacts or join a group.
Agora provides an open-source web Agora Chat UIKit project on GitHub, where you can clone and run the project or reference the logic to create a project that integrates agora-chat-uikit.
- How to get an Agora Chat token
- URL for source code of the Web Agora Chat UIKit
- URL for Agora Chat application using agora-chat-uikit
Currently, agora-chat-uikit
provides the following components:
- Container components:
UIKitProvider
,Chat
,ConversationList
,ContactList
,Thread
; - Module components:
BaseMessage
,AudioMessage
,FileMessage
,VideoMessage
,ImageMessage
,TextMessage
,CombinedMessage
,UserCardMessage
,ContactDetail
,GroupDetail
,Header
,Empty
,MessageList
,ConversationItem
,MessageInput
,MessageStatus
; - Pure UI components:
Avatar
,Badge
,Button
,Checkbox
,Icon
,Modal
,Tooltip
,Input
,UserItem
;
Container components are as follows:
Component | Description | Props | Props Description |
UIKitProvider | The UIKitProvider does not render any UI but only provides global context for components. It automatically listens to SDK events, transmits data downward, and drives component rendering |
initConfig: { appKey: string; userId?: string; token?: string; translationTargetLanguage?: string; useUserInfo?: boolean; useReplacedMessageContents?: boolean; deviceId?: string; maxMessages?: number; } |
appKey: Your app key. userId: Your user ID. If you want UIKIt to automatically log in internally, you need to pass in this parameter and Agora Chat token. token: Agora Chat token. translationTargetLanguage: Translating text messages by setting the target language for translation. useUserInfo: Whether to use the user attribute function. If yes, the UIKit will automatically query the user's user attributes internally to display avatars and nicknames. useReplacedMessageContents: Whether the server returns the sender the text message with the content replaced during text moderation: - `true`: Return the adjusted message to the sender. - (Default) `false`: Return the original message to the sender. deviceId: The unique web device ID. maxMessages: The maximum number of messages that can be displayed in a single conversation. The default value is 200. If the maximum value is exceeded, the messages will be automatically cleared and those messages can be retrieved by pulling more messages. |
local?: {
fallbackLng?: string;
lng?: string;
resources?: {
[key: string]: {
translation: {
[key: string]: string;
};
};
};
}
|
To configure the localized copy, see the parameters of the i18next init method | ||
features?: { chat?:{ header?:{ deleteConversation?: boolean; //... } //... }, conversationList?:{ //... } } | Configure the features you need globally. If the required features are also configured in the component, the configuration in the component shall prevail | ||
theme?:{ primaryColor?: string | number; mode?: 'light' | 'dark'; avatarShape?: 'circle' | 'square'; bubbleShape?: 'ground' | 'square'; componentsShape?: 'ground' | 'square'; } |
primaryColor: Theme color, which can be set with hexadecimal color value or Hue value. mode: Light or dark themes. avatarShape: The shape of the avatar. bubbleShape: The shape of the message bubble. componentsShape: The shape of other components. |
||
presenceMap?: { [key: string]: string | HTMLImageElement; } | Customize the online status of configured users | ||
reactionConfig?: { map: { [key: string]: HTMLImageElement; }; } | |||
ConversationList | Conversation list component | className | Component class name |
style | css properties | ||
showSearchList: boolean | Whether to display the search result list. When using renderHeader, this parameter can be used to control whether to display the search result list. | ||
prefix | css class name prefix | ||
headerProps | Props for the Header component | ||
itemProps | Props for the ConversationItem component | ||
renderHeader?: () => React.ReactNode | Custom rendering header, which receives a function that returns a react node | ||
renderSearch?: () => React.ReactNode | Custom rendering search component, which receives a function that returns a react node | ||
renderItem?:(cvs: Conversation, index: number) => React.ReactNode | Custom rendering item component, which receives a function that returns a react node | ||
onItemClick?: (data: ConversationData[0]) => void | Click on the conversation event to return the data of the current conversation | ||
onSearch?: (e: React.ChangeEvent) => boolean | Search input change event. If the function returns false, it will prevent the default search behavior. Users can search according to their own conditions | ||
Chat | Chat component | className: string | Component CSS class name |
style: React.CSSProperties | CSS properties | ||
prefix: string | CSS class name prefix | ||
headerProps: HeaderProps | props for Header | ||
messageListProps: MsgListProps | Props for the MessageList component | ||
messageInputProps: MessageInputProps | Props for the MessageInput component | ||
rtcConfig: ChatProps['rtcConfig'] | Parameters required when using audio and video calls | ||
renderHeader: (cvs: CurrentCvs) => React.ReactNode | Custom render Header component that takes a function that returns a react node,CurrentCvs is the current conversation | ||
renderMessageList?: () => ReactNode; | Custom render message list component | ||
renderMessageInput?: () => ReactNode; | Custom render message input component | ||
renderEmpty?: () => ReactNode; | Custom render empty pages without a conversation | ||
renderRepliedMessage?: (repliedMessage: ChatSDK.MessageBody | null) => ReactNode; | Custom rendering of replied messages on Input | ||
onOpenThread?:(data: { id: string }) => void; | The callback of clicking on the thread message | ||
onVideoCall?:(data: { channel: string }) => void;; | The callback function for initiating a video call | ||
onAudioCall?:(data: { channel: string }) => void;; | The callback function for initiating a voice call | ||
ContactList | ContactList component | ||
className:string | Component CSS class name | ||
UIKit provides a rootStore that contains all the data. rootStore contains:
- initConfig: UIKit initializes data
- client: Chat SDK instance
- conversationStore: indicates the data related to the conversation list
- messageStore: indicates message-related data
- addressStore: indicates the address book data
Store | Attribute/Method | Description |
conversationStore | ||
currentCvs | Current conversation | |
conversationList | All conversations | |
searchList | The searched conversations | |
setCurrentCvs | Set the current conversation | |
setConversation | Set all conversations | |
deleteConversation | Delete a conversation | |
addConversation | Add a conversation | |
topConversation | Top a conversation | |
modifyConversation | Modifying a conversation | |
messageStore | ||
message | Messages in all conversations, including one-to-one chat(`singleChat`), group chat (`groupChat`), and chat room (`chatRoom`) | |
currentCvsMsgs | Set messages for the current conversation | |
sendMessage | Send a message | |
receiveMessage | Receive a message | |
modifyMessage | Edit a message | |
sendChannelAck | Reply with a channel ack to clear unread data from the conversation | |
updateMessageStatus | Update message status | |
clearMessage | Clear messages of a conversation |
Here is an example of how to customize the chat component.
You can modify the style by passing in className, style, and prefix through the component props:
import { Chat, Button } from 'chatuim2';
const ChatApp = () => {
return (
<div>
<Chat className="customClass" prefix="custom" />
<Button style={{ width: '100px' }}>Button</Button>
</div>
);
};
Custom components can be rendered through the renderX method of container components:
import {Chat, Header} from 'agora-chat-uikit'
const ChatApp = () => {
const CustomHeader = <Header back content="Custom Header">
return(
<div>
<Chat renderHeader={(cvs) => CustomHeader}>
</div>
)
}
The UIKit style is developed using the scss framework and defines a series of global style variables, including but not limited to global styles (main color, background color, rounded corners, borders, font size).
// need to use hsla
$blue-base: hsla(203, 100%, 60%, 1);
$green-base: hsla(155, 100%, 60%, 1);
$red-base: hsla(350, 100%, 60%, 1);
$gray-base: hsla(203, 8%, 60%, 1);
$special-base: hsla(220, 36%, 60%, 1);
$font-color: $gray-3;
$title-color: $gray-1;
$component-background: #fff;
$height-base: 36px;
$height-lg: 48px;
$height-sm: 28px;
// vertical margins
$margin-lg: 24px;
$margin-md: 16px;
$margin-sm: 12px;
$margin-xs: 8px;
$margin-xss: 4px;
// vertical paddings
$padding-lg: 24px;
$padding-md: 20px;
$padding-sm: 16px;
$padding-s: 12px;
$padding-xs: 8px;
$padding-xss: 4px;
// font
$font-size-base: 14px;
$font-size-lg: $font-size-base + 2px;
$font-size-sm: 12px;
$text-color: fade($black, 85%);
- Use webpack for variable coverage:
module.exports = {
module: {
rules: [
{
test: /\.s[ac]ss$/i,
use: [
'style-loader',
'css-loader',
{
loader: 'sass-loader',
options: {
additionalData: `@import "@/styles/index.scss";`,
},
},
],
},
],
},
};
- Customize in create-react-app
Create an SCSS file with variables to override style.scss. Make sure that you import the files in the following order:
@import 'agora-chat-uikit/style.scss'; // agora-chat-uikit theme
@import 'your-theme.scss'; // your theme
@import 'agora-chat-uikit/components.scss'; // components style
If these cannot meet the customization requirements, you can also find the elements to cover the style of UIKit.
If you want to add extra functions to agora-chat-uikit to share with others, you can fork our repository on GitHub and create a pull request. For any issues, please submit it on the repository. Thank you for your contribution!
If you have any problems or suggestions regarding the sample projects, feel free to file an issue.
- Check our FAQ to see if your issue has been recorded.
- Dive into Agora SDK Samples to see more tutorials.
- Take a look at Agora Use Case for more complicated real use case.
- Repositories managed by developer communities can be found at Agora Community.
- For any integration issues, feel free to ask for help in Stack Overflow.
The sample projects are under the MIT license.