初始化 SDK
在应用的 Application 的 onCreate()
方法中做初始化操作,同时我们可以传入一些设置好的 options。
@Override
public void onCreate() {
EMOptions options = initChatOptions();
//初始化
if(options == null){
EMClient.getInstance().init(this, initChatOptions());
} else{
EMClient.getInstance().init(this, options);
}
//在做打包混淆时,关闭debug模式,避免消耗不必要的资源
EMClient.getInstance().setDebugMode(true);
}
private EMOptions initChatOptions(){
EMOptions options = new EMOptions();
// 默认添加好友时,是不需要验证的,改成需要验证
options.setAcceptInvitationAlways(false);
// set if you need read ack
options.setRequireAck(true);
// set if you need delivery ack
options.setRequireDeliveryAck(false);
// 建议初始化SDK的时候设置成每个会话默认load一条消息,节省加载会话的时间
options.setNumberOfMessagesLoaded(1);
//you need apply & set your own id if you want to use google cloud messaging.
options.setGCMNumber("324169311137");
//you need apply & set your own id if you want to use Mi push notification
options.setMipushConfig("2882303761517426801", "5381742660801");
}
需要注意的是,如果应用中有其它第三方的服务启动,那么在初始化环信 SDK 之前需要添加下面相关的代码来防止环信 SDK 被初始化 2 次。
appContext = this;
int pid = android.os.Process.myPid();
String processAppName = getAppName(pid);
// 如果APP启用了远程的service,此application:onCreate会被调用2次
// 为了防止环信SDK被初始化2次,加此判断会保证SDK被初始化1次
// 默认的APP会在以包名为默认的process name下运行,如果查到的process name不是APP的process name就立即返回
if (processAppName == null ||!processAppName.equalsIgnoreCase(appContext.getPackageName())) {
Log.e(TAG, "enter the service process!");
// 则此application::onCreate 是被service 调用的,直接返回
return;
}
...
private String getAppName(int pID) {
String processName = null;
ActivityManager am = (ActivityManager) this.getSystemService(ACTIVITY_SERVICE);
List l = am.getRunningAppProcesses();
Iterator i = l.iterator();
PackageManager pm = this.getPackageManager();
while (i.hasNext()) {
ActivityManager.RunningAppProcessInfo info = (ActivityManager.RunningAppProcessInfo) (i.next());
try {
if (info.pid == pID) {
processName = info.processName;
return processName;
}
} catch (Exception e) {
// Log.d("Process", "Error>> :"+ e.toString());
}
}
return processName;
}
注册
注册模式分两种,开放注册(客户端可以直接注册)和授权注册。
- 开放注册是为了测试使用,正式环境中不推荐使用该方式注册环信账号;
- 授权注册的流程是客户端填写好注册信息后点击注册按钮,注册信息提交到应用服务器,应用服务器提供环信提供的 REST API 进行注册,注册完成后应用服务器进行处理在返回给客户端注册结果。
登录
调用异步方法 login()
完成登录。需要注意的是在登录成功后需要调用 EMClient.getInstance().chatManager().loadAllConversations();
和 EMClient.getInstance().groupManager().loadAllGroups();
这两个方法是为了保证进入主页后本地会话和群组都 load 完毕。
EMClient.getInstance().login(userName,password,new EMCallBack() {//回调
@Override
public void onSuccess() {
EMClient.getInstance().groupManager().loadAllGroups();
EMClient.getInstance().chatManager().loadAllConversations();
Log.d("main", "登录聊天服务器成功!");
}
@Override
public void onProgress(int progress, String status) {
}
@Override
public void onError(int code, String message) {
Log.d("main", "登录聊天服务器失败!");
}
});
另外如果登录过,我们需要在应用的欢迎界面中还要加入上面两个方法来保证进入主页后本地会话和群组都 load 完毕。
在 SplashActivity 类中
if(isLoggedIn()) {
EMClient.getInstance().chatManager().loadAllConversations();
EMClient.getInstance().groupManager().loadAllGroups();
...
startActivity(new Intent(SplashActivity.this, MainActivity.class));
}
public boolean isLoggedIn() {
return EMClient.getInstance().isLoggedInBefore();
}
在我们首次登录成功后,不需要再次调用登录方法。在下次应用启动时,环信 SDK 会自动完成登录。如果自动登录失败,也会读取之前的会话信息。
自动登录在下面几种情况下会被取消:
- 用户调用了 SDK 的登出动作;
- 用户在别的设备上更改了密码,导致此设备上自动登录失败;
- 用户的账号被从服务器端删除;
- 用户从另一个设备登录,把当前设备上登录的用户踢出。
退出登录
// 异步方法
EMClient.getInstance().logout(true, new EMCallBack() {
@Override
public void onSuccess() {
// TODO Auto-generated method stub
}
@Override
public void onProgress(int progress, String status) {
// TODO Auto-generated method stub
}
@Override
public void onError(int code, String message) {
// TODO Auto-generated method stub
}
});
有时候在执行退出登录时,由于网络问题而导致账号解绑失败,即使界面退出,但还会收到消息的现象。为了避免这种情况的发生,我们可以在应用选择退出时弹出对话框显示当前网络是否正常以及提示退出的风险(继续退出可能还会收到消息)。
需要注意的是,如果调用异步退出方法,在收到 onSuccess()
的回调后才去调用 IM 相关的方法,比如 login。
注册连接监听
当掉线时,Android SDK 会自动重连,无需进行任何操作,通过注册连接监听来知道连接状态。根据 onDisconnected()
方法返回的 error 判断账号连接失败的原因。
//注册一个监听连接状态的listener
EMClient.getInstance().addConnectionListener(new MyConnectionListener());
//实现ConnectionListener接口
private class MyConnectionListener implements EMConnectionListener {
@Override
public void onConnected() {
}
@Override
public void onDisconnected(final int error) {
runOnUiThread(new Runnable() {
@Override
public void run() {
if(error == EMError.USER_REMOVED){
// 显示帐号已经被移除
}else if (error == EMError.USER_LOGIN_ANOTHER_DEVICE) {
// 显示帐号在其他设备登录
} else {
if (NetUtils.hasNetwork(MainActivity.this))
//连接不到环信聊天服务器
else
//当前网络不可用,请检查网络设置
}
}
});
}
}
文章只是作为自己记录学习使用,如果有使用不当的地方可以@我,谢谢。
参考文章:环信开发文档