OpenHarmony上编写app
liebian365 2025-01-02 17:42 18 浏览 0 评论
本文将介绍如何使用 cpp 编写用于小型系统的 app。
Ability 相关介绍
Ability 是应用所具备能力的抽象,也是应用程序的重要组成部分。Ability 是系统调度应用的最小单元,是能够完成一个独立功能的组件。
一个应用可以包含一个或多个 Ability。其中 Ability 又分为 Page 类型的和 Service 类型的,前者是为用户提供人机交互能力的,后者是提供后台任务机制的。
简单来讲就是 Page 带界面,Service 不带界面。这里将重点介绍 Page 类型的 Ability。
使用到的子系统有 Ability 子系统、包管理子系统和图形 UI 子系统。
Ability 子系统是管理 OpenHarmony 应用运行状态的开发框架;包管理子系统是 OpenHarmony 为开发者提供的安装包管理框架;图形 UI 子系统提供基础 UI 组件和容器类组件。
简单实现
①ability 和 abilityslice
abilityslice 是单个页面及其控制逻辑的总和,是 Page 类型 Ability 特有的组件。
一个 Page 类型的 Ability 可以包含多个 AbilitySlice,此时,这些页面提供的业务能力应当是高度相关的。
②生命周期
整体流程下来大致有 OnStart()、OnAvtive()、OnInactive()、OnBackground() 和 OnStop() 五阶段。
abilityslice 生命周期与 ability 相似,但是仍要区分。
③hello world?
./helloworld/
├── config.json //配置文件
├── resource //资源
└── src //主要文件
├── include
│ ├── main_ability.h
│ └── main_ability_slice.h
└── main
├── main_ability.cpp
└── main_ability_slice.cpp
首先定义并注册 ability:
// main_ability.h
#ifndef HELLO_MAIN_ABILITY_H
#define HELLO_MAIN_ABILITY_H
#include "ability_loader.h"
namespace OHOS {
class MainAbility : public Ability {
protected:
void OnStart(const Want &want) override; //Want结构体,ability的相关信息
/*
* 由于在这里我们只要简单的展示helloworld标签,其它函数不需要重载。
*/
// void OnInactive() override;
// void OnActive(const Want &want) override;
// void OnBackground() override;
// void OnStop() override;
};
}
#endif
//main_ability.cpp
#include "main_ability.h"
namespace OHOS {
REGISTER_AA(MainAbility) //使用REGISTER_AA注册ability
void MainAbility::OnStart(const Want &want)
{
printf("This is MainAbility OnStart status!\r\n");
SetMainRoute("MainAbilitySlice"); //设置主页面为MainAbilitySlice,这要与后续的slice名字匹配
Ability::OnStart(want);
}
}
最后编写 slice 界面:
//main_ability_slice.h
#ifndef HELLO_ABILITY_SLICE_H
#define HELLO_ABILITY_SLICE_H
#include "ability_loader.h"
#include "ability_manager.h"
#include "bundle_manager.h"
#include "components/ui_label.h"
namespace OHOS {
class MainAbilitySlice : public AbilitySlice { //创建AbilitySlice类 与上面同名
public:
MainAbilitySlice() = default;
virtual ~MainAbilitySlice();
protected:
void OnStart(const Want &want) override;
/*
* 同理
*/
// void OnInactive() override;
// void OnActive(const Want &want) override;
// void OnBackground() override;
// void OnStop() override;
};
}
#endif
//main_ability_slice.cpp
#include "main_ability_slice.h"
const int screen_width = 720;
const int screen_height = 1280;
namespace OHOS {
REGISTER_AS(MainAbilitySlice)
MainAbilitySlice::~MainAbilitySlice()
{
printf("This is ~MainAbilitySlice!\r\n");
}
void MainAbilitySlice::OnStart(const Want& want)
{
AbilitySlice::OnStart(want);
RootView* rootView_ = RootView::GetWindowRootView(); //创建底层界面
rootView_->SetPosition(0, 0, screen_width, screen_height);
rootView_->SetStyle(STYLE_BACKGROUND_COLOR, Color::ColorTo32(Color::Black()));
rootView_->SetFocusable(true);
rootView_->SetInterceptFocus(false);
UILabel* label = new UILabel(); //创建label写入Hello World
label->SetPosition(0, 0, 720, 64);
label->SetText("Hello World!");
label->SetFont("SourceHanSansSC-Regular.otf", 64);
label->SetStyle(STYLE_TEXT_COLOR, Color::ColorTo32(Color::White()));
rootView_->Add(label); //将label放入rootView
SetUIContent(rootView_); //设置显示RootView UI
}
}
#endif
④config.json 的编写
//config.json
{
"app": {
"bundleName": "com.sample.hello",
"vendor": "sample",
"version": {
"code": 1,
"name": "1.0"
},
"apiVersion": {
"compatible": 3,
"target": 4
}
},
"deviceConfig": {
"default": {
}
},
"module": {
"package": "com.sample.hello",
"name": ".MyHarmonyAbilityPackage",
"deviceType": [
"phone",
"tv",
"tablet",
"pc",
"car",
"smartWatch",
"sportsWatch",
"smartVision"
],
"distro": {
"deliveryWithInstall": true,
"moduleName": "hello",
"moduleType": "entry"
},
"abilities": [ //ability配置声明
{
"name": "MainAbility",
"label": "hello world app",
"launchType": "standard",
"type": "page",
"visible": true
}
]
}
}
hap 编译
①通过 BUILD.gn 与系统一并编译
使用到编译链中的 hap_pack,添加配置:
import(“/ildte/config/hap_pack.gni”)
import("//build/lite/config/hap_pack.gni")
shared_library("hello") {
sources = [
"src/main/main_ability.cpp",
"src/main/main_ability_slice.cpp"
] #将主要文件编译出库
deps = [
"${aafwk_lite_path}/frameworks/ability_lite:aafwk_abilitykit_lite",
"${appexecfwk_lite_path}/frameworks/bundle_lite:bundle",
"//foundation/graphic/ui:lite_ui",
"//foundation/graphic/utils:lite_graphic_utils",
"//foundation/systemabilitymgr/samgr_lite/samgr:samgr",
]
include_dirs = [
"src/include",
"${aafwk_lite_path}/interfaces/kits/ability_lite",
"${aafwk_lite_path}/interfaces/kits/want_lite",
"${appexecfwk_lite_path}/interfaces/kits/bundle_lite",
]
ldflags = [ "-shared" ]
ldflags += [ "-lstdc++" ]
ldflags += [ "-L$ohos_root_path/sysroot/usr/lib" ]
ldflags += [ "-Wl,-rpath-link=$ohos_root_path/sysroot/usr/lib" ]
ldflags += [
"-lui",
"-lability",
] #添加依赖
defines = [
"ENABLE_WINDOW=1",
"ABILITY_WINDOW_SUPPORT",
"OHOS_APPEXECFWK_BMS_BUNDLEMANAGER",
] #配置定义
}
hap_pack("hello_hap") { #打包成hap
deps = [ ":hello" ]
mode = "hap"
json_path = "config.json"
ability_so_path = "$root_out_dir/libhello.so" #编译后的库文件
force = "true"
cert_profile = "com.huawei.launcher_AppProvision_release.p7b" #由于不清楚获取证书方法 先用源码案例自带的证书代替
resources_path = "resources"
hap_name = "hello"
}
②通过 app_packing_tool 单独编译
该打包工具在源码目录 developtools/packing_tool/jar 下。
主要参数如下:
具体操作:还是得先将动态库编译出来,然后将动态库 libhello.so 和 config.json 放到一个文件夹里。
./out/
├── config.json
└── libhello.so
最后使用 java -jar app_packing_tool.jar 进行打包,如下:
java -jar app_packing_tool.jar |
--mode hap |
--json-path ./config.json |
--ability-out-path ./libhello.so |
--out-path ./hello.hap
hap 安装
①安装命令 bm?
由于小型系统不支持使用 HDC 工具,我们需要使用到 bm 命令进行安装程序。
bm set -s disable //取消签名安装。
bm install -p system/internal/hello.hap //使用BUILD.gn一起编译的hap默认会在这个路径,如果使用工具打包的,视情况填写路径。
②相关参数?
# bm
Usage: install hap-path [options]
Description:
--help|-h help menu
--happath|-p location of the hap to install
Usage: uninstall bundle-name [options]
Description:
--help|-h help menu
--bundlename|-n name of the bundle to uninstall
Usage: dump [options]
Option Description:
--help|-h help menu
--list|-l app list
--bundlename|-n dump installed hap's info
--metadatakey|-m dump bundleNames match metaData key
Usage: set [options]
Option Description:
--externalmode|-e status enable externalmode
--debugmode|-d status enable debugmode
--signmode|-s status enable signmode
小型系统的 bm 指令是标准系统的阉割版。
安装成功后就可以打开该 app,部分小型系统的设备屏幕没有触摸功能和鼠标驱动,我们可以使用 aa 命令来启动 app。
aa start -p com.sample.hello -n MainAbility //包名和ability名都在config.json中定义
# aa
Usage:
aa start -p bundlename -n ability_name
aa stopability -p bundlename -n ability_name
aa terminate -p bundlename
aa dump -p bundlename -n ability_name -e extra_option
aa dump -a
Options:
-h (--help) Show the help information. [eg: aa -h]
-p (--bundlename) Appoint the bundlename name. [eg: -p com.huawei]
-n (--abilityname) Appoint the ability name. [eg: -n MyAbility]
-a (--all) [Unnecessary]dump all ability info. [eg: -a]
-e (--extra) [Unnecessary]extra info when dump. [eg: -e]
Commands:
aa start Start the target ability.
aa stopability Stop the target service ability.
aa terminate Terminate the target app.
aa dump Dump ability
总结
使用 cpp 编写用户应用程序,我们可以更方便有效的调用南向接口,这将会在开发和调试的过程中给我们带来极大的便利。
- 上一篇:Perfetto工具集之traced_perf
- 下一篇:一文汇总开源鸿蒙蓝牙能力
相关推荐
- python如何对字符串进行操作(python如何对字符串进行操作输出)
-
1.字符串的创建可通过直接赋值、构造或转义字符来创建字符串。#普通字符串s="Hello,World!"#多行字符串(使用三引号)multi_line_str='''Thisi...
- Excel表格中11个常用的字符串函数
-
今天和大家聊聊常用的字符串函数,在不同的条件下,如何选择字符串函数很关键。下面我为大家列举了11个关于字符串的函数公式。一、EXACT(两个字符串进行结果比较)比较两个字符串是否完全相同(这里是要区分...
- 详细介绍一下Python中如何对字符串进行操作?
-
在Python中,字符串做为一种常见的数据处理类型,几乎在每个应用程序中都会被用到。而作为Python中使用最广泛的数据类型Python也是提供了很多强大的方法来支持对于字符串的处理操作。下面我们就来...
- Java中你知道几种从字符串中找指定的字符的数量
-
遇到这样的问题,常规的思路估计就是遍历String,然后逐个对比。下面先看循环遍历循环遍历privatestaticintgetNum(StringoriginStr,Stringtarg...
- C语言strcspn函数详解:字符串的“扫雷探测器”
-
strcspn是C语言标准库中的一个函数,定义在头文件中。它用于计算从字符串的开始到首次出现任何属于指定字符集合的字符之间的字符数量。换句话说,strcspn计算的是主字符串中不包含指定字符集...
- 如何使用 Python 的 f-string 进行字符串格式化
-
Python中的字符串格式化曾经有点麻烦。必须在...
- java判断字符串中是否包含某个字符
-
1使用String类的contains()方法contains()方法用于判断字符串中是否包含指定的字符或字符串。语法如下:publicbooleancontains(CharSequence...
- Python基础:f-string不同数据类型的格式化选项,终极指南!
-
上一篇文章我们介绍了4种字符串格式化方法,其中最现代、最直观的方式是f-string,从Python3.6开始引入,而且时不时就增加一些超级优雅的小改进。今天,钢铁老豆想要继续给大家展开介绍不同数据...
- Excel查找指定字符串,返回相应的结果
-
通过下面的函数,可以实现查找指定字符串,若找到返回“有”,若找不到返回“无”。=IF(ISNUMBER(SEARCH("失业",G3)),"有","无")...
- 一个list中,有b.a.b.c.b.b.写个方法去掉所有b
-
importjava.util.ArrayList;importjava.util.List;publicclassRemoveBFromStringList{/**...
- 掌握Python f-string(掌握催眠能力之后的日常生活)
-
f-string,通常称为格式化字符串文本,是Python3.6中添加的一项强大功能,它提供了一种将表达式包含在字符串文本中的清晰实用的方法。,...
- 深入了解字符串:定义、转义字符和字符串下标
-
字符串是编程中常见的数据类型之一,用于表示文本信息。在绝大多数编程语言中,字符串都是由一系列字符组成的序列,可以包含字母、数字、符号以及空格等。字符串的定义:...
- 100个Java工具类之70:字符串处理工具类StringUtils
-
StringUtils是常用的工具类,提供大量处理字符串的静态方法。StringUtils主要特点...
- Shell中针对字符串的切片,截取,替换,删除,大小写操作
-
切片返回字符串变量var的长度...
- Sqlite - 常规函数 - RTRIM(sqlite命令行工具)
-
在SQLite中,RTRIM函数是一个用于处理字符串的函数,其主要作用是移除字符串右侧(尾部)的指定字符。如果不指定要移除的字符,默认会移除字符串右侧的空格字符。以下是对RTRIM函数的详细...
你 发表评论:
欢迎- 一周热门
- 最近发表
- 标签列表
-
- wireshark怎么抓包 (75)
- qt sleep (64)
- cs1.6指令代码大全 (55)
- factory-method (60)
- sqlite3_bind_blob (52)
- hibernate update (63)
- c++ base64 (70)
- nc 命令 (52)
- wm_close (51)
- epollin (51)
- sqlca.sqlcode (57)
- lua ipairs (60)
- tv_usec (64)
- 命令行进入文件夹 (53)
- postgresql array (57)
- statfs函数 (57)
- .project文件 (54)
- lua require (56)
- for_each (67)
- c#工厂模式 (57)
- wxsqlite3 (66)
- dmesg -c (58)
- fopen参数 (53)
- tar -zxvf -c (55)
- 速递查询 (52)