NearbyService超簡單整合教程get!助你打造一款更加便捷的社交聊天類應用
背景
“附近的人”、“面對面建群”、“近距離點對點本地聊天”…這幾個常見的功能都會出現在各大社交類軟體中。可通常情況下,“附近的人”基本都只能發現距離自己幾百米甚至幾公里以外的人,如何縮小這個距離,實現與數米距離內的人打招呼呢?“面對面建群”如何精確的發現就在自己身邊的人呢?如何不經過雲服務即可直接通訊與好友聊天呢?Nearby Service都可以幫你實現!下面將為大家詳細講解Nearby Service整合教程,助你打造一款更加便捷的社交聊天類應用。
應用場景介紹
這裡為大家帶來一個集成了Nearby Service的示例應用,這個應用利用Nearby Service能做到發現附近的人,以及基於這個能力可以實現如面對面建群、群聊、私密聊、遷移聊天記錄等功能。
- 附近的人
可以為使用者精準的發現附近數米的人,支援使用者發現同處一室的朋友,如會議室、展廳、酒吧、咖啡廳等;
- 面對面建群
利用Nearby Service進行建群,只需在端側即可完成建群動作,位置精確,只有同處一地的人能夠進群。
- 隨心聊
利用Nearby Service可以實現近距離範圍內不加好友的群聊,新朋友只需到範圍附近即可自動入群;離開對應範圍自動退出。
- 私密聊
利用Nearby Service可以實現近距離本地點對點聊天。通訊只在兩個裝置間進行,資料加密不上雲,無需擔心資訊洩露;在高鐵、地鐵等訊號不好的場所時也可以進行通訊。
- 遷移聊天記錄
不僅如此,Nearby Service還提供了強大的檔案傳輸功能。當用戶有多個裝置需要遷移聊天記錄時,可利用Nearby Service的通訊介面,實現高速、免流量的資料遷移。
工具準備
-
2檯安卓手機或更多
-
開發工具 Android Studio(3.X or later)
構建示例應用
-
在Android Studio中匯入示例原始碼。
-
註冊成為華為開發者。
-
參考Nearby Service 開發準備在華為應用市場建立一個您的應用。注意:需要下載“agconnect-services.json”檔案和參考指導生成簽名證書並放置在app/目錄下。
-
使用adb命令將生成的apk檔案安裝到測試手機。
關鍵程式碼
示例應用中使用的介面在官方文件Nearby Service Guides中有詳細的介紹。
這個示例應用採用MVP的模式進行構建,如您想檢視原始碼,請根據程式碼路徑: com\huawei\hms\nearby\im找到相應的類。
1. 附近的人
如下面程式碼所示NearbyPeoplePresenter類在初始化時需將view物件傳入。當呼叫NearbyPeoplePresenter.findNearbyPeople()發現附近的人時,呼叫view的介面執行後續的動作。
INearbyPeopleView和後面步驟中的xxxView是一組介面,它們的具體實現是對應的Activity物件,程式碼路徑是:com\huawei\hms\nearby\im\ui\adapter。
public NearbyPeoplePresenter(Context mContext, INearbyPeopleView view) {
super(mContext, view);
nearbyAgent = new NearbyAgent(mContext, new NearbyAgent.INearbyMessageView() {
@Override
public void onMessageFound(MessageBean messageBean) {
// notify view when found someone
view.onMemberChanged(false,messageBean);
}
@Override
public void onMessageLost(MessageBean messageBean) {
view.onMemberChanged(true,messageBean);
}
@Override
public void onMsgSendResult(boolean isSucceed, MessageBean item) {
view.onLoginResult(isSucceed,item);
if (!isSucceed) {
handler.postDelayed(() -> findNearbyPeople(),DURATION_RE_LOGIN);
}
}
});
handler = new Handler(Looper.getMainLooper());
}
public void findNearbyPeople() {
nearbyAgent.broadcastMessage(null,MessageBean.ACTION_TAG_ONLINE);
nearbyAgent.startScan();
}
2. 面對面建群
與“附近的人”類似,CreateGroupPresenter.java類在初始化時傳入view物件,當呼叫joinGroup(groupId)介面時會加入該群組,結果會通過呼叫view的介面返回。
public CreateGroupPresenter(Context mContext, ICreateGroupView view) {
super(mContext, view);
nearbyAgent = new NearbyAgent(mContext, new NearbyAgent.INearbyMessageView() {
@Override
public void onMessageFound(MessageBean messageBean) {
view.onPeopleFound(messageBean);
}
@Override
public void onMessageLost(MessageBean messageBean) {}
@Override
public void onMsgSendResult(boolean isSucceed, MessageBean item) {
view.onJoinGroupResult(isSucceed,item);
}
});
}
public void joinGroup(String groupId) {
nearbyAgent.broadcastMessage(groupId,"join group");
nearbyAgent.startScan(groupId);
}
3. 隨心聊
類GroupChatPresenter.java在初始化時需傳入view物件。業務程式碼呼叫broadcastMessage(groupId, sendContent)傳送訊息到指定的群組,groupId為空時不限定群組;呼叫findMessage(groupId)發現指定群組的訊息,發現後呼叫view介面返回訊息。
public GroupChatPresenter(Context mContext, IGroupChatView view) {
super(mContext, view);
nearbyAgent = new NearbyAgent(mContext, new NearbyAgent.INearbyMessageView() {
@Override
public void onMessageFound(MessageBean messageBean) {
view.onMessageFound(messageBean);
}
@Override
public void onMessageLost(MessageBean messageBean) {
}
@Override
public void onMsgSendResult(boolean isSucceed, MessageBean item) {
view.onMsgSendResult(isSucceed,item);
}
});
}
public void broadcastMessage(String groupId, String sendContent) {
nearbyAgent.broadcastMessage(groupId,sendContent);
}
public void findMessage(String groupId) {
nearbyAgent.startScan(groupId);
}
4. 私密聊
私密聊的實現與上述介面有所不同,類NearbyConnectionPresenter.java提供了4個介面:
-
findNearbyPeople():發現附近的人
-
requestConnect():與對方建立連線
-
sendMessage(String msgStr):傳送字串型別訊息
-
sendFile(Uri uri):傳送檔案
/**
* scanAndBroadcasting to find nearby people
*/
public void findNearbyPeople(){
mDiscoveryEngine.startScan(serviceId, new ScanEndpointCallback() {
@Override
public void onFound(String endpointId, ScanEndpointInfo discoveryEndpointInfo) {
Log.d(TAG, "onFound -- Nearby Connection Demo app: onFound endpoint: " + endpointId);
view.onFound(endpointId,discoveryEndpointInfo);
}
@Override
public void onLost(String endpointId) {
Log.d(TAG, "onLost -- Nearby Connection Demo app: Lost endpoint: " + endpointId);
view.onLost(endpointId);
}
}, scanOption);
}
/**
* request to connect with remote device
* @param endpointId the endpointId of remote device
*/
public void requestConnect(String endpointId) {
Log.d(TAG, "requestConnect -- endpoint: " + endpointId);
mDiscoveryEngine.requestConnect(myNameStr, endpointId, connectCallback);
}
/**
* Send message ,Data.Type.BYTES
*/
public MessageBean sendMessage(String msgStr) {
MessageBean item = new MessageBean();
item.setUserName(CommonUtil.userName);
item.setMsg(msgStr);
item.setType(MessageBean.TYPE_SEND_TEXT);
item.setSendTime(DateUtils.getCurrentTime(DateUtils.FORMAT));
Data data = Data.fromBytes(gson.toJson(item).getBytes(Charset.defaultCharset()));
mTransferEngine.sendData(mEndpointId, data);
return item;
}
/**
* send file ,Data.Type.FILE
* @param uri
*/
public Data sendFile(Uri uri) {
Data filePayload;
try {
ParcelFileDescriptor pfd = mContext.getContentResolver().openFileDescriptor(uri, "r");
filePayload = Data.fromFile(pfd);
} catch (FileNotFoundException e) {
Log.e(Constants.TAG, "File not found, cause: ", e);
return null;
}
String fileName = FileUtil.getFileRealNameFromUri(mContext, uri);
String filenameMessage = filePayload.getId() + ":" + fileName;
Data filenameBytesPayload = Data.fromBytes(filenameMessage.getBytes(StandardCharsets.UTF_8));
mTransferEngine.sendData(mEndpointId, filenameBytesPayload);
mTransferEngine.sendData(mEndpointId, filePayload);
return filePayload;
}
更多詳情
-
華為開發者聯盟官網:
https://developer.huawei.com/consumer/en/hms/huawei-nearbyservice?ha_source=hms1 -
參與開發者討論請到Reddit社群:https://www.reddit.com/r/HuaweiDevelopers/
-
下載demo和示例程式碼請到Github:https://github.com/HMS-Core
-
解決整合問題請到Stack Overflow:
https://stackoverflow.com/questions/tagged/huawei-mobile-services?tab=Newest
原文連結:
https://developer.huawei.com/consumer/cn/forum/topic/0201415949786580446?fid=18&pid=0301415949786580897
作者:胡椒