基于华为开发者空间鸿蒙云手机+MaaS的鸿蒙原生智能应用开发 - 翻译助手APP
本案例通过鸿蒙应用开发工具DevEco Studio、测试工具DevEco Testing远程连接鸿蒙云手机,集成华为云MaaS,开发调试鸿蒙原生应用-翻译助手APP。
最新案例动态,请查阅基于华为开发者空间鸿蒙云手机+MaaS的鸿蒙原生智能应用开发 - 翻译助手APP。小伙伴们快来进行实操吧!
一、概述
1.1 案例介绍
鸿蒙云手机是基于华为鸿蒙操作系统(HarmonyOS)的云端虚拟化手机服务,通过云计算技术将手机功能迁移至云端,为用户提供跨终端、高性能的移动体验。
MaaS(MaaS模型即服务)是华为云面向AI开发者推出的一站式大模型开发平台,支持开发者一键体验大模型能力,快速构建大模型应用。Mass平台提供大模型训练、推理、部署、管理、监控等全生命周期管理能力,帮助开发者快速构建大模型应用,加速AI开发。
DevEco Studio 是 HarmonyOS 应用及服务的集成开发环境(IDE),提供了一站式的开发平台,包括代码编辑、编译构建、代码调试、性能调优、模拟器、应用测试等能力。
DevEco Testing提供一站式的应用测试服务平台。为开发者提供稳定性、性能、应用基础质量等专项测试服务,覆盖应用测试全周期,助力打造高品质应用。
本案例通过鸿蒙应用开发工具DevEco Studio、测试工具DevEco Testing远程连接鸿蒙云手机,集成华为云MaaS,开发调试鸿蒙原生应用-翻译助手APP。
1.2 适用对象
- 企业
- 个人开发者
- 高校学生
1.3 案例时间
本案例总时长预计90分钟。
1.4 案例流程
说明:
- 开发者下载开发工具DevEco Studio和测试工具DevEco Testing;
- 领取华为云MaaS平台大模型Tokens福利;
- 用户登录开发者空间,创建并远程连接鸿蒙云手机;
- 使用鸿蒙云手机调试运行翻译助手APP代码。
1.5 资源总览
本案例预计花费0或1元。
| 资源名称 | 规格 | 单价(元) |
|---|---|---|
| 华为开发者空间 - 鸿蒙云手机 | HarmonyOS | 8vCPUs | 12G | 2720x1260 | 免费 |
| 华为开发者空间 - DeepSeek-R1/V3.2千万Tokens代金券 | DeepSeekV3.2 | 1.00 |
| ModelArts Studio大模型(DS/K2/Q3等)通用代金券 | DeepSeekV3.2 | 0.00 |
| DevEco Studio | 6.0.0 Release | 免费 |
| DevEco Testing | 6.0.7.202 | 免费 |
二、基础环境与资源准备
2.1 获取AK/SK及工具下载
登录华为开发者空间,参考案例《华为开发者空间-鸿蒙云手机操作指导手册(Windows)》中的“二、环境及资源准备”章节内容,获取AK/SK、下载开发工具(DevEco Studio)与测试工具(DevEco Testing)。
2.2 领取华为云MaaS平台大模型Tokens福利(任选其一)
方式一: 登录华为开发者空间,参考案例《华为开发者空间 - ModelArts Studio大模型通用代金券领取使用指导》中的“二、 开通MaaS平台大模型”章节内容领取代金券,获取到模型的API地址、模型名称和API Key。
方式二: 登录华为开发者空间,参考案例《华为云MaaS平台大模型Tokens领取使用指导》中的“二、 领取MaaS平台大模型Tokens”章节内容,领取MaaS平台DeepSeek V3系列大模型Tokens代金券,购买ModelArts Studio DeepSeek Tokens套餐包,开通模型服务,最后获取到模型的API地址、模型名称和API Key。
注意:记录API Key、API地址以及模型名称留作后面步骤使用。
三、远程连接鸿蒙云手机
注意:鸿蒙云手机目前处于公测中,按照以下步骤参与公测,在线开发与调试鸿蒙应用。
登录华为开发者空间,点击鸿蒙云手机,选择职业,输入使用的业务场景,参与公测。
公测申请将在1~3个工作日内审核完成。
审核完成后,即可创建和使用鸿蒙云手机。
参考案例《华为开发者空间-鸿蒙云手机操作指导手册(Windows)》中的“三、鸿蒙云手机操作指导”的内容,完成“1. 创建鸿蒙云手机 ~ 4. DevEco Studio连接云手机”章节步骤。
四、翻译助手APP代码实践
4.1 项目介绍
本项目集成AI能力,提供主流语言(包括汉语、英语、法语、俄语、西班牙语、阿拉伯语、德语)互译能力,输入需要翻译的语言,点击翻译按钮,即可将输入的语言文字翻译成目标语言。
4.2 项目结构
TranslationAssistant:项目名称
- AppScope > app.json5:应用的全局配置信息。
- entry:HarmonyOS工程模块,编译构建生成一个HAP包。
-
src > main > ets:用于存放ArkTS源码。
- bean:
- MessageBean.ets、ModelMessageBean.ets、ModelResultBean.ets:华为云MaaS API返回数据封装。
- entryability:
- EntryAbility.ets应用/服务的入口。
- entrybackupability:
- EntryBackupAbility.ets:应用提供扩展的备份恢复能力。
- model:
- IndexViewModel.ets:返回数据model层封装,解析并获取模型数据。
- ImagesViewModel.ets:首页轮播图片数据获取。
- pages:
- Index.ets:应用主界面。
- utils:
- HttpHelper.ets:网络请求工具类。
- Logger.ets:日志打印工具类。
- ModelConstants.ets:常量配置工具类。
- view:
- UploadingLayout.ets:自定义网络加载组件。
- bean:
-
src > main > resources:用于存放应用/服务所用到的资源文件,如图形、多媒体、字符串、布局文件等。
-
src > main > module.json5:模块配置文件。
-
build-profile.json5:当前的模块信息 、编译信息配置项,包括buildOption、targets配置等。
-
hvigorfile.ts:模块级编译构建任务脚本。
-
obfuscation-rules.txt:混淆规则文件。混淆开启后,在使用Release模式进行编译时,会对代码进行编译、混淆及压缩处理,保护代码资产。
-
oh-package.json5:用来描述包名、版本、入口文件(类型声明文件)和依赖项等信息。
-
- oh_modules:用于存放三方库依赖信息。
- build-profile.json5:工程级配置信息,包括签名signingConfigs、产品配置products等。其中products中可配置当前运行环境,默认为HarmonyOS。
- hvigorfile.ts:工程级编译构建任务脚本。
- oh-package.json5:主要用来描述全局配置。
4.3 核心代码解析
4.3.1 应用主界面
**pages/Index.ets:**翻译助手的主界面,用户在此界面选择需要翻译的语种,输入语言文字,点击翻译按钮,即可将对应的语言翻译成目标语言并提供复制功能。
Index.ets完整代码如下:
import mainViewModel from '../model/ImagesViewModel';
import pasteboard from '@ohos.pasteboard';
import promptAction from '@ohos.promptAction';
import UploadingLayout from '../view/UploadingLayout';
import Logger from '../utils/Logger';
import DetailViewModel from '../model/IndexViewModel';
@Entry
@Component
struct Index {
private languageArray: Array<string> = ['汉语', '英语', '法语', '俄语', '西班牙语', '阿拉伯语', '德语'];
private swiperController: SwiperController = new SwiperController();
@State translationResult: string = '';
@State fromLanguage: string = '汉语';
@State toLanguage: string = '英语';
@State isUploading: boolean = false;
@State select: number = 0;
@State prompt: string = ""
content: string = "";
textImage?: Resource;
title?: ResourceStr;
onFromItemClick = (): void => {
this.getUIContext().showTextPickerDialog({
range: this.languageArray,
selected: this.select,
canLoop: false,
onAccept: (value: TextPickerResult) => {
this.select = value.index as number;
this.fromLanguage = value.value as string;
},
onChange: (value: TextPickerResult) => {
this.select = value.index as number;
}
})
};
onToItemClick = (): void => {
this.getUIContext().showTextPickerDialog({
range: this.languageArray,
selected: this.select,
canLoop: false,
onAccept: (value: TextPickerResult) => {
this.select = value.index as number;
this.toLanguage = value.value as string;
},
onChange: (value: TextPickerResult) => {
this.select = value.index as number;
}
})
};
build() {
Stack() {
Column() {
Swiper(this.swiperController) {
ForEach(mainViewModel.getSwiperImages(), (img: Resource) => {
Image(img)
.height('200vp')
.width('100%')
}, (img: Resource) => JSON.stringify(img.id))
}
.autoPlay(true)
Row() {
Row() {
Text(this.fromLanguage)
.fontSize(17)
.layoutWeight(0.85)
.margin({ left: 10 })
.height('100%')
Row() {
Image($r('app.media.icon_down'))
.width(13)
.height(13)
}
.layoutWeight(0.15)
}
.layoutWeight(1)
.border({ width: 0.8, color: Color.Gray, style: BorderStyle.Solid })
.borderRadius(10)
.backgroundColor(Color.White)
.onClick(this.onFromItemClick)
Image($r('app.media.icon_trans'))
.width(20)
.height(20)
.margin({ left: 5, right: 5 })
Row() {
Text(this.toLanguage)
.fontSize(17)
.margin({ left: 16 })
.layoutWeight(0.85)
.height('100%')
Row() {
Image($r('app.media.icon_down'))
.width(13)
.height(13)
}
.layoutWeight(0.15)
}
.layoutWeight(1)
.borderRadius(10)
.border({ width: 0.8, color: Color.Gray, style: BorderStyle.Solid })
.backgroundColor(Color.White)
.onClick(this.onToItemClick)
}.height(50).margin({ left: 5, right: 5, top: 10 })
Stack({ alignContent: Alignment.BottomEnd }) {
TextArea({ placeholder: '请输入文字' })
.border({ width: 0.8, color: Color.Gray, style: BorderStyle.Solid })
.placeholderFont({ size: "16fp" })
.width('98%')
.fontColor("#182431")
.height("150vp")
.borderRadius(10)
.fontSize("16fp")
.margin({ top: "10vp" })
.backgroundColor(Color.White)
.onChange((value: string) => {
this.content = value;
})
Button('翻译')
.width('20%')
.height('35vp')
.margin({ bottom: "10vp", right: "10vp" })
.fontSize('18fp')
.onClick(() => {
this.translateLanguage();
})
.fontWeight(FontWeight.Medium)
.backgroundColor('#007DFF')
}
Column() {
Stack({ alignContent: Alignment.BottomEnd }) {
Text(this.translationResult)
.fontColor("#182431")
.align(Alignment.Top)
.padding('10vp')
.width('98%')
.height("280vp")
.borderRadius(10)
.fontSize("16fp")
.border({ width: 0.8, color: Color.Gray, style: BorderStyle.Solid })
.margin({ top: "10vp" })
.backgroundColor(Color.White)
Button('复制')
.width('20%')
.height('35vp')
.margin({ bottom: "10vp", right: "10vp" })
.fontSize('18fp')
.fontWeight(FontWeight.Medium)
.onClick(() => {
this.copyText();
})
.backgroundColor('#007DFF')
}
}
}
.backgroundColor('#F1F3F5')
.width("100%")
.height("100%")
if (this.isUploading) {
UploadingLayout()
}
}
}
/**
* 复制文本到剪贴板的方法
*/
async copyText() {
if (!this.translationResult) {
promptAction.showToast({ message: '内容为空' });
return;
}
try {
let systemPasteboard = pasteboard.getSystemPasteboard();
await systemPasteboard.setData(pasteboard.createData(pasteboard.MIMETYPE_TEXT_PLAIN, this.translationResult));
// 提示用户
promptAction.showToast({ message: '复制成功', duration: 1000 });
} catch (err) {
console.error('Copy failed:', JSON.stringify(err));
promptAction.showToast({ message: '复制失败' });
}
}
async translateLanguage() {
if (!this.content) {
promptAction.showToast({ message: '请输入文字' });
return;
}
this.prompt = `您好,请将下面这句话:${this.content},从${this.fromLanguage}翻译成${this.toLanguage}`;
Logger.info(`prompt: ${this.prompt}`);
this.isUploading = true
DetailViewModel.requestModelData(this.prompt).then((content) => {
Logger.info(`content: ${content}`);
this.isUploading = false
if (!content) {
promptAction.showToast({ message: '请求失败' });
return;
}
this.translationResult = content
})
}
}
4.3.2 添加网络权限
鸿蒙系统提供一种通用权限访问方式,允许应用访问系统资源(如通讯录)和系统能力(如摄像头、麦克风),以保护系统数据(包括用户个人数据)和功能,防止不当或恶意使用。访问网络需要在配置文件声明权限。
在entry->src->main->module.json5文件中声明网络权限:
"requestPermissions": [
{
"name": "ohos.permission.INTERNET"
}
],
4.3.3 模型数据获取
封装网络请求工具类HttpHelper,用于获取模型返回的数据。
HttpHelper.ets:
HttpHelper.ets完整代码如下:
import { http } from '@kit.NetworkKit';
import { ModelResultBean } from '../bean/ModelResultBean';
import Logger from './Logger';
import { ModelConstants } from './ModelConstants';
class HttpHelper {
async requestData(prompt: string): Promise<string> {
// 每一个httpRequest对应一个HTTP请求任务,不可复用
let httpRequest = http.createHttp();
// 用于订阅HTTP响应头,此接口会比request请求先返回。可以根据业务需要订阅此消息
httpRequest.on('headersReceive', (header) => {
console.info('header: ' + JSON.stringify(header));
});
let options: http.HttpRequestOptions = {
method: http.RequestMethod.POST,
// 开发者根据自身业务需要添加header字段
header: {
'Content-Type': 'application/json',
// 把yourApiKey替换成真实的API Key
"Authorization": `${ModelConstants.API_KEY}`
},
// 当使用POST请求时此字段用于传递请求体内容,具体格式与服务端协商确定
extraData: {
"model": `${ModelConstants.MODEL_NAME}`,
"messages": [
{ "role": "system", "content": "You are a helpful assistant." },
{ "role": "user", "content": prompt }
],
"stream": false,
"temperature": 0.6
},
// 可选,指定返回数据的类型
expectDataType: http.HttpDataType.STRING,
// 可选,默认为true
usingCache: true,
// 可选,默认为1
priority: 1,
// 可选,默认为60000ms
connectTimeout: 60000,
// 可选,默认为60000ms
readTimeout: 60000,
// 可选,协议类型默认值由系统自动指定
usingProtocol: http.HttpProtocol.HTTP1_1,
}
let messageResult: string = ''
try {
let httpResponse = await httpRequest.request(ModelConstants.API_URL, options)
let responseCode = httpResponse.responseCode
let responseResult = httpResponse.result as string
Logger.info(`responseResult: ${responseResult}`);
Logger.info(`responseCode: ${responseCode}`);
if (responseCode == 200) {
let modelResultBean = JSON.parse(responseResult) as ModelResultBean
messageResult = JSON.stringify(modelResultBean.choices)
Logger.info(`messageResult: ${messageResult}`);
} else {
messageResult = ""
}
} catch (err) {
Logger.info(`messageResult: ${JSON.stringify(err)}`);
messageResult = ""
}
httpRequest.off('headersReceive');
// 当该请求使用完毕时,调用destroy方法主动销毁
httpRequest.destroy();
return messageResult
}
}
export default new HttpHelper();
注意:替换ModelConstants.ets文件中的常量MODEL_NAME、API_URL、API_KEY。
ModelConstants.ets:
export class ModelConstants {
static readonly API_URL: string = 'YOUR_API_URL';
static readonly MODEL_NAME: string = 'YOUR_MODEL_NAME';
static readonly API_KEY: string = 'Bearer YOUR_API_KEY';
}
- YOUR_API_URL:替换成步骤“2.2 领取华为云MaaS平台大模型Tokens福利”中获取的API地址。
- YOUR_MODEL_NAME:替换成步骤“2.2 领取华为云MaaS平台大模型Tokens福利”中获取的模型名称。
- YOUR_API_KEY:替换成步骤“2.2 领取华为云MaaS平台大模型Tokens福利”中获取的API Key。
4.4 调试运行代码
源码下载:TranslationAssistant,下载解压完成后,使用DevEco Studio打开项目源码:
修改项目级目录下build-profile.json5文件中sdk编译版本。因为鸿蒙云手机是鸿蒙5.0,所以需要修改代码编译sdk版本,compatibleSdkVersion修改为:5.0.5(17)
替换src/main/ets/utils/ModelConstants.ets文件中的常量。
- YOUR_API_URL:替换成步骤“2.2 领取华为云MaaS平台大模型Tokens福利”中获取的API地址。
- YOUR_MODEL_NAME:替换成步骤“2.2 领取华为云MaaS平台大模型Tokens福利”中获取的模型名称。
- YOUR_API_KEY:替换成步骤“2.2 领取华为云MaaS平台大模型Tokens福利”中获取的API Key。
DevEco Studio编译器连接云手机后,点击右上角运行按钮,运行项目代码:
打开DevEco Testing,选择【标准】模式,翻译助手APP代码已经运行在鸿蒙云手机上了。
汉语翻译成英语:
汉语翻译成俄语:
至此,基于华为开发者空间鸿蒙云手机+MaaS的鸿蒙原生智能应用开发-翻译助手APP的案例已全部完成。
五、反馈改进建议
如您在案例实操过程中遇到问题或有改进建议,可以到论坛帖评论区反馈即可,我们会及时响应处理,谢谢!
更多推荐




所有评论(0)