当前位置: 首页 > news >正文

开源 Arkts 鸿蒙应用 开发(九)通讯--tcp客户端

 

  文章的目的为了记录使用Arkts 进行Harmony app 开发学习的经历。本职为嵌入式软件开发,公司安排开发app,临时学习,完成app的开发。开发流程和要点有些记忆模糊,赶紧记录,防止忘记。

 相关链接:

开源 Arkts 鸿蒙应用 开发(一)工程文件分析-CSDN博客

开源 Arkts 鸿蒙应用 开发(二)封装库.har制作和应用-CSDN博客

开源 Arkts 鸿蒙应用 开发(三)Arkts的介绍-CSDN博客

开源 Arkts 鸿蒙应用 开发(四)布局和常用控件-CSDN博客

开源 Arkts 鸿蒙应用 开发(五)控件组成和复杂控件-CSDN博客

开源 Arkts 鸿蒙应用 开发(六)数据持久--文件和首选项存储-CSDN博客

开源 Arkts 鸿蒙应用 开发(七)数据持久--sqlite关系数据库-CSDN博客

开源 Arkts 鸿蒙应用 开发(八)多媒体--相册和相机-CSDN博客

开源 Arkts 鸿蒙应用 开发(九)通讯--tcp客户端-CSDN博客

 推荐链接:

开源 java android app 开发(一)开发环境的搭建-CSDN博客

开源 java android app 开发(二)工程文件结构-CSDN博客

开源 java android app 开发(三)GUI界面布局和常用组件-CSDN博客

开源 java android app 开发(四)GUI界面重要组件-CSDN博客

开源 java android app 开发(五)文件和数据库存储-CSDN博客

开源 java android app 开发(六)多媒体使用-CSDN博客

开源 java android app 开发(七)通讯之Tcp和Http-CSDN博客

开源 java android app 开发(八)通讯之Mqtt和Ble-CSDN博客

开源 java android app 开发(九)后台之线程和服务-CSDN博客

开源 java android app 开发(十)广播机制-CSDN博客

开源 java android app 开发(十一)调试、发布-CSDN博客

开源 java android app 开发(十二)封库.aar-CSDN博客

推荐链接:

开源C# .net mvc 开发(一)WEB搭建_c#部署web程序-CSDN博客

开源 C# .net mvc 开发(二)网站快速搭建_c#网站开发-CSDN博客

开源 C# .net mvc 开发(三)WEB内外网访问(VS发布、IIS配置网站、花生壳外网穿刺访问)_c# mvc 域名下不可訪問內網,內網下可以訪問域名-CSDN博客

开源 C# .net mvc 开发(四)工程结构、页面提交以及显示_c#工程结构-CSDN博客

开源 C# .net mvc 开发(五)常用代码快速开发_c# mvc开发-CSDN博客

本章内容主要是演示鸿蒙的tcp客户端的通讯:

实现TCP客户端功能,可以连接指定IP和端口的服务器。支持发送和接收文本消息,显示连接状态和通信历史。

新建DevEco的工程,选择Empty Ability,只需要修改module.json5,和Index.ets文件,就可以实现TCP客户端的APP。

一、设置权限,修改module.json5文件。

文件位置

module.json5代码

{"module": {"name": "entry","type": "entry","description": "$string:module_desc","mainElement": "EntryAbility","deviceTypes": ["phone"],"deliveryWithInstall": true,"installationFree": false,"pages": "$profile:main_pages","abilities": [{"name": "EntryAbility","srcEntry": "./ets/entryability/EntryAbility.ets","description": "$string:EntryAbility_desc","icon": "$media:layered_image","label": "$string:EntryAbility_label","startWindowIcon": "$media:startIcon","startWindowBackground": "$color:start_window_background","exported": true,"skills": [{"entities": ["entity.system.home"],"actions": ["action.system.home"]}]}],"extensionAbilities": [{"name": "EntryBackupAbility","srcEntry": "./ets/entrybackupability/EntryBackupAbility.ets","type": "backup","exported": false,"metadata": [{"name": "ohos.extension.backup","resource": "$profile:backup_config"}],}],"requestPermissions": [{"name": "ohos.permission.INTERNET"}]}
}

二、Index.ets的代码

// MainAbility.ets
import socket from '@ohos.net.socket';
import common from '@ohos.app.ability.common';
import promptAction from '@ohos.promptAction';
import { BusinessError } from '@kit.BasicServicesKit';@Entry
@Component
struct TcpClientPage {@State serverIp: string = '192.168.3.146'; // 默认服务器IP@State serverPort: string = '1000'; // 默认端口@State message: string = ''; // 要发送的消息@State receivedData: string = ''; // 接收到的数据@State isConnected: boolean = false; // 连接状态private tcpSocket: socket.TCPSocket = socket.constructTCPSocketInstance();private context = getContext(this) as common.UIAbilityContext;// 初始化TCP套接字aboutToAppear() {this.tcpSocket = socket.constructTCPSocketInstance();// 设置TCP连接参数let tcpOptions: socket.TCPConnectOptions = {address: {address: this.serverIp,port: parseInt(this.serverPort),family: 1 // 1表示IPv4},timeout: 5000 // 连接超时时间5秒};// 监听接收数据this.tcpSocket.on('message', (messageInfo: socket.SocketMessageInfo) => {console.info('Received message');// 从 SocketMessageInfo 中获取 ArrayBufferconst buffer = messageInfo.message; // message 是 ArrayBuffer 类型const data = this.arrayBufferToString(buffer);this.receivedData += `[接收] ${new Date().toLocaleTimeString()}: ${data}\n`;});// 监听连接关闭this.tcpSocket.on('close', () => {console.info('Connection closed');this.isConnected = false;promptAction.showToast({ message: '连接已关闭', duration: 2000 });});// 监听错误事件this.tcpSocket.on('error', (err) => {console.error('Socket error: ' + JSON.stringify(err));promptAction.showToast({ message: '发生错误: ' + JSON.stringify(err), duration: 3000 });this.isConnected = false;});}private arrayBufferToString(buffer: ArrayBuffer): string {const uint8Array = new Uint8Array(buffer);let str = '';for (let i = 0; i < uint8Array.length; i++) {str += String.fromCharCode(uint8Array[i]);}return str;}// 字符串转ArrayBufferprivate stringToArrayBuffer(str: string): ArrayBuffer {let buf = new ArrayBuffer(str.length);let bufView = new Uint8Array(buf);for (let i = 0; i < str.length; i++) {bufView[i] = str.charCodeAt(i);}return buf;}// 连接/断开服务器private toggleConnection() {if (this.isConnected) {this.disconnect();} else {this.connect();}}// 连接到服务器private async connect() {try {let tcpOptions: socket.TCPConnectOptions = {address: {address: this.serverIp,port: parseInt(this.serverPort),family: 1},timeout: 5000};await this.tcpSocket.connect(tcpOptions);this.isConnected = true;promptAction.showToast({ message: '连接成功', duration: 2000 });// 开始接收数据this.tcpSocket.getState().then(state => {console.info('Socket state: ' + JSON.stringify(state));});} catch (err) {console.error('Connect failed: ' + JSON.stringify(err));promptAction.showToast({ message: '连接失败: ' + JSON.stringify(err), duration: 3000 });this.isConnected = false;}}// 断开连接private disconnect() {try {this.tcpSocket.close();this.isConnected = false;promptAction.showToast({ message: '已断开连接', duration: 2000 });} catch (err) {console.error('Disconnect failed: ' + JSON.stringify(err));promptAction.showToast({ message: '断开连接失败: ' + JSON.stringify(err), duration: 3000 });}}private sendMessage() {if (!this.isConnected) {promptAction.showToast({ message: '请先连接到服务器', duration: 2000 });return;}if (!this.message.trim()) {promptAction.showToast({ message: '消息不能为空', duration: 2000 });return;}try {const buffer = this.stringToArrayBuffer(this.message);this.tcpSocket.send({ data: buffer }).then(() => {this.receivedData += `[发送] ${new Date().toLocaleTimeString()}: ${this.message}\n`;this.message = '';}).catch((err: BusinessError) => {console.error(`Send failed: code=${err.code}, message=${err.message}`);promptAction.showToast({ message: `发送失败: ${err.message}`, duration: 3000 });});} catch (err) {console.error(`Send error: code=${err.code}, message=${err.message}`);promptAction.showToast({ message: `发送错误: ${err.message}`, duration: 3000 });}}build() {Column({ space: 10 }) {// 标题Text('TCP客户端').fontSize(24).fontWeight(FontWeight.Bold).margin({ bottom: 20 })// 服务器地址输入Row({ space: 10 }) {Text('服务器IP:').fontSize(16).width(80)TextInput({ text: this.serverIp }).width('60%').onChange((value: string) => {this.serverIp = value;})}.width('100%').justifyContent(FlexAlign.Start)// 端口号输入Row({ space: 10 }) {Text('端口号:').fontSize(16).width(80)TextInput({ text: this.serverPort }).width('60%').onChange((value: string) => {this.serverPort = value;})}.width('100%').justifyContent(FlexAlign.Start)// 连接按钮Button(this.isConnected ? '断开连接' : '连接').width('80%').height(40).backgroundColor(this.isConnected ? '#ff4d4f' : '#1890ff').onClick(() => {this.toggleConnection();})// 消息输入框TextInput({ placeholder: '输入要发送的消息', text: this.message }).width('90%').height(60).margin({ top: 20 }).onChange((value: string) => {this.message = value;})// 发送按钮Button('发送').width('80%').height(40).margin({ top: 10 }).onClick(() => {this.sendMessage();})// 消息显示区域Scroll() {Text(this.receivedData).width('90%').fontSize(14).textAlign(TextAlign.Start).padding(10).backgroundColor('#f5f5f5')}.width('100%').height(200).margin({ top: 20 }).border({ width: 1, color: '#d9d9d9' })}.width('100%').height('100%').padding(20).justifyContent(FlexAlign.Start)}
}

三、效果演示

3.1  首先搭建服务器端,这里使用了网络调试助手,设置ip和端口号,

3.2  APP的效果和设置


文章转载自:
http://neigh .dxwdwl.cn
http://tafoni .dxwdwl.cn
http://informer .dxwdwl.cn
http://bowfin .dxwdwl.cn
http://sonifier .dxwdwl.cn
http://answerer .dxwdwl.cn
http://jabiru .dxwdwl.cn
http://fattest .dxwdwl.cn
http://sulfonamide .dxwdwl.cn
http://galactosidase .dxwdwl.cn
http://rotundity .dxwdwl.cn
http://fixt .dxwdwl.cn
http://rewin .dxwdwl.cn
http://synectic .dxwdwl.cn
http://bifid .dxwdwl.cn
http://lotta .dxwdwl.cn
http://ristocetin .dxwdwl.cn
http://heres .dxwdwl.cn
http://demonophobia .dxwdwl.cn
http://snottynose .dxwdwl.cn
http://mythical .dxwdwl.cn
http://fender .dxwdwl.cn
http://nasturtium .dxwdwl.cn
http://arbitrage .dxwdwl.cn
http://aerobus .dxwdwl.cn
http://chasten .dxwdwl.cn
http://contend .dxwdwl.cn
http://survivalist .dxwdwl.cn
http://peroration .dxwdwl.cn
http://garniture .dxwdwl.cn
http://www.dtcms.com/a/293758.html

相关文章:

  • 在 Ubuntu 20.04.5 LTS 系统上安装 Docker CE 26.1.4 完整指南
  • Spring Cloud Alibaba Sentinel 基本工作原理源码阅读
  • MACOS安装配置Gradle
  • 国产数据库转向 “融合” 赛道:电科金仓的下一代形态定义之路
  • 基于Matlab传统图像处理技术的车辆车型识别与分类方法研究
  • 资本押注会成长的玩具,AI潮玩赛道开始升温
  • 华为云ELB(弹性负载均衡)持续报异常
  • 永磁同步电机控制算法--弱磁控制(负载能力最大化的定交轴)
  • 【C++】C++ 的入门语法知识1
  • 在easyui中如何设置自带的弹窗,有输入框
  • 解决Spring事务中RPC调用无法回滚的问题
  • 零基础学编程,编程从入门到精通系列教程,附:编程工具箱之时间计算构件的用法#零基础自学编程 学习计划#新手学编程 高效学习方法
  • HF83311_VB1/HF83311Q_VB1:高性能USB HiFi音频解码器固件技术解析
  • Leetcode-15. 三数之和
  • 《计算机“十万个为什么”》之 [特殊字符] 深浅拷贝 引用拷贝:内存世界的复制魔法 ✨
  • 1.1 Deep learning?pytorch ?深度学习训练出来的模型通常有效但无法解释合理性? 如何 解释?
  • 英语词汇积累Day1-10(summary)
  • Django实战:Python代码规范指南
  • 【Java】Reflection反射(代理模式)
  • 算法竞赛备赛——【图论】最小生成树
  • 《元素周期表》超高清PDF
  • IDEA如何管理多个Java版本。
  • STM32 基础知识 定时器【概念】
  • 基于PyTorch的多视角二维流场切片三维流场预测模型
  • 【NLP舆情分析】基于python微博舆情分析可视化系统(flask+pandas+echarts) 视频教程 - 主页-微博点赞量Top6实现
  • 19.动态路由协议基础
  • 备受关注的“Facebook Email Scraper”如何操作?
  • 开源 Arkts 鸿蒙应用 开发(十)通讯--Http
  • 腾讯云推出CodeBuddy:革新AI全栈开发体验
  • 第六章 W55MH32 UDP Multicast示例