衡阳派盒市场营销有限公司

0
  • 聊天消息
  • 系統消息
  • 評論與回復
登錄后你可以
  • 下載海量資料
  • 學習在線課程
  • 觀看技術視頻
  • 寫文章/發帖/加入社區
會員中心
創作中心

完善資料讓更多小伙伴認識你,還能領取20積分哦,立即完善>

3天內不再提示

基于鴻蒙分布式數據服務開發的聊天室應用

OpenHarmony技術社區 ? 來源:HarmonyOS技術社區 ? 作者:梁青松 ? 2021-12-03 10:35 ? 次閱讀

之前給大家介紹過《HarmonyOS 分布式之仿抖音應用》,此次給大家介紹一下基于鴻蒙分布式數據服務開發的聊天室應用,模擬現實中的聊天室對話,可以與小伙伴們互動、分享自己的故事給小伙伴。

主要知識點

分布式數據服務

https://developer.harmonyos.com/cn/docs/documentation/doc-guides/database-mdds-guidelines-0000000000030122

官方介紹:分布式數據服務主要實現用戶設備中應用程序的數據內容的分布式同步。

當設備 1 上的應用 A 在分布式數據庫中增、刪、改數據后,設備 2 上的應用 A 也可以獲取到該數據庫變化,總結一句話:多個設備共用一個數據庫。

主頁代碼

沒有特別復雜的邏輯,主要是分布式數據服務的使用,關鍵地方都有注釋。
importcom.ldd.myapp.bean.ChatDataBean;
importcom.ldd.myapp.provider.ChatProvider;
importcom.ldd.myapp.util.Tools;
importohos.aafwk.ability.AbilitySlice;
importohos.aafwk.content.Intent;
importohos.agp.components.Button;
importohos.agp.components.ListContainer;
importohos.agp.components.TextField;
importohos.app.Context;
importohos.bundle.IBundleManager;
importohos.data.distributed.common.*;
importohos.data.distributed.user.SingleKvStore;
importohos.utils.zson.ZSONArray;
importohos.utils.zson.ZSONObject;

importjava.util.ArrayList;
importjava.util.List;

importstaticohos.security.SystemPermission.DISTRIBUTED_DATASYNC;

/**
*主頁
*/
publicclassMainAbilitySliceextendsAbilitySlice{
privateContextmContext;
//聊天列表
privateListContainerlcList;
//聊天數據
privatefinalListlistData=newArrayList<>();
//聊天數據適配器
privateChatProviderchatProvider;
//輸入框
privateTextFieldtfContent;
//發送按鈕
privateButtonbtnSend;

//分布式數據庫管理器
privateKvManagerkvManager;
//分布式數據庫
privateSingleKvStoresingleKvStore;
//數據庫名稱
privatestaticfinalStringSTORE_NAME="ChatStore";
//存入的列表數據key
privatestaticfinalStringKEY_DATA="key_data";
//存入的頭像索引
privatestaticfinalStringKEY_PIC_INDEX="key_pic_index";
privateintpicIndex=0;

@Override
publicvoidonStart(Intentintent){
super.onStart(intent);
super.setUIContent(ResourceTable.Layout_ability_main);
mContext=this;
requestPermission();
initComponent();
initDatabase();
}

/**
*請求分布式權限
*/
privatevoidrequestPermission(){
if(verifySelfPermission(DISTRIBUTED_DATASYNC)!=IBundleManager.PERMISSION_GRANTED){
if(canRequestPermission(DISTRIBUTED_DATASYNC)){
requestPermissionsFromUser(newString[]{DISTRIBUTED_DATASYNC},0);
}
}
}

/**
*初始化組件
*/
privatevoidinitComponent(){
lcList=(ListContainer)findComponentById(ResourceTable.Id_lc_list);
tfContent=(TextField)findComponentById(ResourceTable.Id_tf_content);
tfContent.setAdjustInputPanel(true);
btnSend=(Button)findComponentById(ResourceTable.Id_btn_send);
btnSend.setEnabled(false);

//初始化適配器
chatProvider=newChatProvider(mContext,listData);
lcList.setItemProvider(chatProvider);

//輸入框內容變化監聽
tfContent.addTextObserver((text,start,before,count)->{
btnSend.setEnabled(text.length()!=0);
});
//點擊發送按鈕
btnSend.setClickedListener(component->{
Stringcontent=tfContent.getText().trim();
listData.add(newChatDataBean(Tools.getDeviceId(mContext),picIndex,content));
//存入數據庫中
singleKvStore.putString(KEY_DATA,ZSONObject.toZSONString(listData));

//清空輸入框
tfContent.setText("");
});
}

/**
*初始化分布式數據庫
*/
privatevoidinitDatabase(){
//創建分布式數據庫管理器
kvManager=KvManagerFactory.getInstance().createKvManager(newKvManagerConfig(this));

//數據庫配置
Optionsoptions=newOptions();
options.setCreateIfMissing(true)//設置數據庫不存在時是否創建
.setEncrypt(false)//設置數據庫是否加密
.setKvStoreType(KvStoreType.SINGLE_VERSION);//數據庫類型
//創建分布式數據庫
singleKvStore=kvManager.getKvStore(options,STORE_NAME);
//監聽數據庫數據改變
singleKvStore.subscribe(SubscribeType.SUBSCRIBE_TYPE_ALL,newKvStoreObserver(){
@Override
publicvoidonChange(ChangeNotificationchangeNotification){
ListinsertEntries=changeNotification.getInsertEntries();
ListupdateEntries=changeNotification.getUpdateEntries();

//第一次存入數據,獲取insertEntries
if(insertEntries.size()>0){
for(Entryentry:insertEntries){
if(KEY_DATA.equals(entry.getKey())){
//回調為非UI線程,需要在UI線程更新UI
getUITaskDispatcher().syncDispatch(()->{
listData.clear();
listData.addAll(ZSONArray.stringToClassList(entry.getValue().getString(),ChatDataBean.class));
chatProvider.notifyDataChanged();
lcList.scrollTo(listData.size()-1);
});
}
}
}elseif(updateEntries.size()>0){
for(Entryentry:updateEntries){
if(KEY_DATA.equals(entry.getKey())){
//回調為非UI線程,需要在UI線程更新UI
getUITaskDispatcher().syncDispatch(()->{
listData.clear();
listData.addAll(ZSONArray.stringToClassList(entry.getValue().getString(),ChatDataBean.class));
chatProvider.notifyDataChanged();
lcList.scrollTo(listData.size()-1);
});
}
}
}
}
});

try{
picIndex=singleKvStore.getInt(KEY_PIC_INDEX);
singleKvStore.putInt(KEY_PIC_INDEX,picIndex+1);
}catch(KvStoreExceptione){
e.printStackTrace();
//沒有找到,首次進入
if(e.getKvStoreErrorCode()==KvStoreErrorCode.KEY_NOT_FOUND){
picIndex=0;
singleKvStore.putInt(KEY_PIC_INDEX,picIndex+1);
}
}
}

@Override
protectedvoidonStop(){
super.onStop();
kvManager.closeKvStore(singleKvStore);
}
}

簡單案例

config.json 配置:
"reqPermissions":[
{
"reason":"多設備協同",
"name":"ohos.permission.DISTRIBUTED_DATASYNC",
"usedScene":{
"ability":[
"MainAbility"
],
"when":"always"
}
},
{
"name":"ohos.permission.DISTRIBUTED_DEVICE_STATE_CHANGE"
},
{
"name":"ohos.permission.GET_DISTRIBUTED_DEVICE_INFO"
},
{
"name":"ohos.permission.GET_BUNDLE_INFO"
}
]

布局頁面:

<DirectionalLayout
xmlns:ohos="http://schemas.huawei.com/res/ohos"
ohos:height="match_parent"
ohos:width="match_parent"
ohos:alignment="center"
ohos:orientation="vertical">

<Text
ohos:id="$+id:text"
ohos:height="match_content"
ohos:width="match_content"
ohos:text="數據:0"
ohos:text_size="15fp"/>

<Button
ohos:margin="20vp"
ohos:id="$+id:button"
ohos:height="match_content"
ohos:width="match_parent"
ohos:background_element="$graphic:button_bg"
ohos:padding="10vp"
ohos:text="點擊+1"
ohos:text_color="white"
ohos:text_size="15fp"/>

DirectionalLayout>
MainAbilitySlice 代碼:
importohos.aafwk.ability.AbilitySlice;
importohos.aafwk.content.Intent;
importohos.agp.components.Button;
importohos.agp.components.ListContainer;
importohos.agp.components.Text;
importohos.agp.components.TextField;
importohos.bundle.IBundleManager;
importohos.data.distributed.common.*;
importohos.data.distributed.user.SingleKvStore;
importohos.utils.zson.ZSONArray;

importjava.util.List;

importstaticohos.security.SystemPermission.DISTRIBUTED_DATASYNC;

publicclassMainAbilitySliceextendsAbilitySlice{
//顯示數據
privateTexttext;
//分布式數據庫管理器
privateKvManagerkvManager;
//分布式數據庫
privateSingleKvStoresingleKvStore;
//數據庫名稱
privatestaticfinalStringSTORE_NAME="MyStore";
//存入的數據key
privatestaticfinalStringKEY_COUNT="key_count";

@Override
publicvoidonStart(Intentintent){
super.onStart(intent);
super.setUIContent(ResourceTable.Layout_ability_main);
requestPermission();
initDatabase();
initComponent();
}

/**
*請求分布式權限
*/
privatevoidrequestPermission(){
if(verifySelfPermission(DISTRIBUTED_DATASYNC)!=IBundleManager.PERMISSION_GRANTED){
if(canRequestPermission(DISTRIBUTED_DATASYNC)){
requestPermissionsFromUser(newString[]{DISTRIBUTED_DATASYNC},0);
}
}
}

/**
*初始化分布式數據庫
*/
privatevoidinitDatabase(){
//創建分布式數據庫管理器
kvManager=KvManagerFactory.getInstance().createKvManager(newKvManagerConfig(this));

//數據庫配置
Optionsoptions=newOptions();
options.setCreateIfMissing(true)//設置數據庫不存在時是否創建
.setEncrypt(false)//設置數據庫是否加密
.setKvStoreType(KvStoreType.SINGLE_VERSION);//數據庫類型
//創建分布式數據庫
singleKvStore=kvManager.getKvStore(options,STORE_NAME);
//監聽數據庫數據改變
singleKvStore.subscribe(SubscribeType.SUBSCRIBE_TYPE_ALL,newKvStoreObserver(){
@Override
publicvoidonChange(ChangeNotificationchangeNotification){
ListinsertEntries=changeNotification.getInsertEntries();
ListupdateEntries=changeNotification.getUpdateEntries();

//第一次存入數據,獲取insertEntries
if(insertEntries.size()>0){
for(Entryentry:insertEntries){
if(KEY_COUNT.equals(entry.getKey())){
//回調為非UI線程,需要在UI線程更新UI
getUITaskDispatcher().syncDispatch(()->{
intcount=entry.getValue().getInt();
text.setText("數據:"+count);
});
}
}
}elseif(updateEntries.size()>0){
for(Entryentry:updateEntries){
if(KEY_COUNT.equals(entry.getKey())){
//回調為非UI線程,需要在UI線程更新UI
getUITaskDispatcher().syncDispatch(()->{
intcount=entry.getValue().getInt();
text.setText("數據:"+count);
});
}
}
}
}
});

}

/**
*初始化組件
*/
privatevoidinitComponent(){
text=(Text)findComponentById(ResourceTable.Id_text);
Buttonbutton=(Button)findComponentById(ResourceTable.Id_button);

//點擊事件
button.setClickedListener(component->{
try{
intcount=singleKvStore.getInt(KEY_COUNT);
singleKvStore.putInt(KEY_COUNT,count+1);
}catch(KvStoreExceptione){
e.printStackTrace();
//沒有找到,首次進入
if(e.getKvStoreErrorCode()==KvStoreErrorCode.KEY_NOT_FOUND){
intcount=0;
singleKvStore.putInt(KEY_COUNT,count+1);
}
}
});
}
}
注釋比較詳細,主要注意 2 個點:
  • 獲取數據時加入 try catch 塊,處理 key 未找到的情況。

  • 數據庫數據改變監聽回調是非 UI 線程,如果更新 UI 必須切換到 UI 線程。

以上簡單案例就是讓你快速掌握分布式數據服務:多個設備相同的應用之間使用同一個數據庫。 項目地址(需要登錄才能看到演示圖):
https://gitee.com/liangdidi/DistributedChatDemo.git
作者:梁青松
編輯:jq
聲明:本文內容及配圖由入駐作者撰寫或者入駐合作網站授權轉載。文章觀點僅代表作者本人,不代表電子發燒友網立場。文章及其配圖僅供工程師學習之用,如有內容侵權或者其他違規問題,請聯系本站處理。 舉報投訴
  • 數據
    +關注

    關注

    8

    文章

    7139

    瀏覽量

    89568
  • 數據庫
    +關注

    關注

    7

    文章

    3846

    瀏覽量

    64684
  • ui
    ui
    +關注

    關注

    0

    文章

    204

    瀏覽量

    21418
  • 代碼
    +關注

    關注

    30

    文章

    4825

    瀏覽量

    69038

原文標題:一款鴻蒙分布式聊天室應用!

文章出處:【微信號:gh_834c4b3d87fe,微信公眾號:OpenHarmony技術社區】歡迎添加關注!文章轉載請注明出處。

收藏 人收藏

    評論

    相關推薦

    分布式云化數據庫有哪些類型

    分布式云化數據庫有哪些類型?分布式云化數據庫主要類型包括:關系型分布式數據庫、非關系型分布式數據
    的頭像 發表于 01-15 09:43 ?110次閱讀

    AIGC入門及鴻蒙入門

    JDK、配置SDK等。 3. 開發實踐: 學習鴻蒙系統的架構和API,了解其組件化、分布式等特性。 通過官方文檔和社區資源,學習和掌握鴻蒙應用的開發
    發表于 01-13 10:32

    HarmonyOS Next 應用元服務開發-分布式數據對象遷移數據文件資產遷移

    設備文件訪問實現文件的遷移,難以獲取文件同步完成的時間。為了保證更高的成功率,文件的遷移不建議繼續通過該方式實現,推薦使用分布式數據對象攜帶資產的方式。開發者此前通過跨設備文件訪問實現的文件遷移依然生效
    發表于 12-24 10:11

    HarmonyOS Next 應用元服務開發-分布式數據對象遷移數據權限與基礎數據

    設備文件訪問實現文件的遷移,難以獲取文件同步完成的時間。為了保證更高的成功率,文件的遷移不建議繼續通過該方式實現,推薦使用分布式數據對象攜帶資產的方式。開發者此前通過跨設備文件訪問實現的文件遷移依然生效
    發表于 12-24 09:40

    鴻蒙ArkTS聲明開發:跨平臺支持列表【分布式遷移標識】 通用屬性

    組件的分布式遷移標識,指明了該組件在分布式遷移場景下可以將特定狀態恢復到對端設備。
    的頭像 發表于 06-07 21:15 ?441次閱讀

    鴻蒙開發接口數據管理:【@ohos.data.distributedDataObject (分布式數據對象)】

    本模塊提供管理基本數據對象的相關能力,包括創建、查詢、刪除、修改、訂閱等;同時支持相同應用多設備間的分布式數據對象協同能力。
    的頭像 發表于 06-07 17:51 ?1550次閱讀
    <b class='flag-5'>鴻蒙</b><b class='flag-5'>開發</b>接口<b class='flag-5'>數據</b>管理:【@ohos.data.distributedDataObject (<b class='flag-5'>分布式</b><b class='flag-5'>數據</b>對象)】

    鴻蒙開發接口數據管理:【@ohos.data.distributedData (分布式數據管理)】

    分布式數據管理為應用程序提供不同設備間數據庫的分布式協同能力。通過調用分布式數據各個接口,應用程
    的頭像 發表于 06-07 09:30 ?1070次閱讀
    <b class='flag-5'>鴻蒙</b><b class='flag-5'>開發</b>接口<b class='flag-5'>數據</b>管理:【@ohos.data.distributedData (<b class='flag-5'>分布式</b><b class='flag-5'>數據</b>管理)】

    HarmonyOS開發實例:【分布式數據服務

    分布式數據服務(Distributed Data Service,DDS)為應用程序提供不同設備間數據分布式的能力。
    的頭像 發表于 04-18 10:18 ?794次閱讀
    HarmonyOS<b class='flag-5'>開發</b>實例:【<b class='flag-5'>分布式</b><b class='flag-5'>數據服務</b>】

    OpenHarmony南向開發案例:【分布式畫板】

    使用OpenHarmony3.1-Release開發的應用。通過OpenHarmony的分布式技術,使多人能夠一起畫畫。
    的頭像 發表于 04-12 14:40 ?1093次閱讀
    OpenHarmony南向<b class='flag-5'>開發</b>案例:【<b class='flag-5'>分布式</b>畫板】

    HarmonyOS開發實例:【分布式數據管理】

    eTS中分布式數據管理的使用,包括KVManager對象實例的創建和KVStore數據流轉的使用。
    的頭像 發表于 04-11 09:57 ?982次閱讀
    HarmonyOS<b class='flag-5'>開發</b>實例:【<b class='flag-5'>分布式</b><b class='flag-5'>數據</b>管理】

    鴻蒙HarmonyOS開發實例:【分布式關系型數據庫】

    使用[@ohos.data.relationalStore]接口和[@ohos.distributedDeviceManager]?接口展示了在eTS中分布式關系型數據庫的使用,在增、刪、改、查的基本操作外,還包括分布式數據庫的
    的頭像 發表于 04-11 09:52 ?1015次閱讀
    <b class='flag-5'>鴻蒙</b>HarmonyOS<b class='flag-5'>開發</b>實例:【<b class='flag-5'>分布式</b>關系型<b class='flag-5'>數據</b>庫】

    鴻蒙HarmonyOS開發實戰:【分布式音樂播放】

    本示例使用fileIo獲取指定音頻文件,并通過AudioPlayer完成了音樂的播放完成了基本的音樂播放、暫停、上一曲、下一曲功能;并使用DeviceManager完成了分布式設備列表的顯示和分布式能力完成了音樂播放狀態的跨設備分享。
    的頭像 發表于 04-10 17:51 ?943次閱讀
    <b class='flag-5'>鴻蒙</b>HarmonyOS<b class='flag-5'>開發</b>實戰:【<b class='flag-5'>分布式</b>音樂播放】

    UEFIRC:運行于UEFI環境下的IRC聊天室

    據悉,開源開發者Phillip Tennen展示了基于UEFI的沉浸IRC網絡聊天室:UREFIRC原型設計。該設計無需進入操作系統,僅在UEFI環境內運行。
    的頭像 發表于 04-08 16:16 ?627次閱讀

    分布式存儲與計算:大數據時代的解決方案

    分布式存儲和計算技術應運而生,并迅速成為處理大數據的首選方案。本文將深入探討分布式存儲和計算的概念、優勢及其在各個領域的應用情況。 1.分布式存儲和計算的概念與優勢
    的頭像 發表于 03-07 14:42 ?861次閱讀

    鴻蒙實戰項目開發:【短信服務

    數據管理 電話服務 分布式應用開發 通知與窗口管理 多媒體技術 安全技能 任務管理 WebGL 國際化開發 應用測試 DFX面向未來設計
    發表于 03-03 21:29
    百家乐官网导航网| 大发888官方正版网| 百家乐官网娱乐代理| 大丰收娱乐城开户| 百家乐群html| 百家乐官网论坛博彩啦| 百家乐赢钱公式| 澳门百家乐规| 百家乐怎么赢博彩正网| 百家乐官网在线娱乐场| 精英百家乐官网现金网| 香港六合彩全年资料| 百家乐官网现金网信誉排名| 大发888娱乐场下载iyou qrd| 百家乐官网优惠现金| 威尼斯人娱乐百利宫| 网上百家乐的打法| 二八杠网站| 现场百家乐投注| 百樂坊百家乐官网的玩法技巧和规则| 优博百家乐官网现金网平台| 东方市| 大发888屡败屡战| 百家乐看图赢钱| 百家乐官网软件代理| 百盛百家乐官网软件| 百家乐官网硬币打法| 奇博| 博狗备用| bet365贴吧| 大发888游戏平台hg dafa 888 gw| 百家乐高手怎么下注| 百家乐赌博在线娱乐| 百家乐娱乐城返水| 网上百家乐官网群的微博| 恒丰百家乐官网的玩法技巧和规则 | 找真人百家乐的玩法技巧和规则 | 香港百家乐官网玩| 万龙百家乐官网的玩法技巧和规则| 百家乐官网在线投注网| 澳门百家乐官网大揭密|