目录
(七) 高通手机跑AI系列之——人像与背景分割-CSDN博客
(一)AidLux 服务进程被杀死(Android 12 及以上系统)
一、AidLux 简介
AidLux 是一款基于 ARM 架构的跨生态(Android / 鸿蒙 + Linux)一站式 AIOT 应用开发平台。它能在安卓手机上直接运行,为开发者提供了原生 Android 和原生 Linux 的使用体验。借助 AidLux,开发者可以便捷地在手机端进行 Python 编程,实现各类 AI 和其他应用的开发。
二、下载与安装 AidLux
(一)下载方式
- 应用市场下载:打开安卓手机的应用商城,在搜索框中输入 “AidLux”,点击搜索结果中的 AidLux 应用,然后点击 “下载” 按钮,等待下载完成。此方法较为便捷,推荐使用。
- 官网下载:在手机浏览器中访问AidLux 官方网站下载最新版本。
(二)安装过程
下载完成后,点击安装包进行安装。安装过程中,手机可能会提示需要授予 AidLux 一些系统权限,如媒体和文件、相机、麦克风、后台弹窗等,务必全部授予,以确保 AidLux 能正常运行各项功能。
三、初始化与登录 AidLux
(一)初始化系统
首次打开 AidLux 应用,软件将进行 Linux 环境配置。该环节依据网络环境及手机硬件性能的不同,大约耗时 1 - 3 分钟。请耐心等待,在此期间保持网络连接稳定。
(二)登录设置
初始化完成后,进入登录界面。输入注册时使用的账号和密码进行登录。若首次登录,需设置新密码。设置密码时,请牢记密码,以便后续登录使用,记得登录,避免运行代码时出现异常。
(三)电脑远程访问 AidLux 主要有以下几种方法
- 通过浏览器访问
- 查看被访问设备 IP:在 AidLux 设备上,点击 Aid 桌面的 “Cloud_ip” 应用,界面上显示的地址即为被访问设备 IP。也可打开 Aid 桌面的 “terminal” 或 “Aid Linux 终端”,输入命令 “ifconfig | grep 'inet' | grep -v '127.0.0.1'” 来查看,找到其中的 ipv4 地址。另外,还能依次点击 “系统设置”→“WLAN”→“当前连接的 WIFI”,查看当前连接 WIFI 的详细信息,找到 IP 地址中的 ipv4 地址。需注意,ipv6 地址暂不支持,使用热点连接时,访问设备需连接到被访问设备的热点。
- 访问 Aid 桌面:Aid 桌面支持远程访问,处于同一局域网的电脑可通过浏览器访问该桌面。Aid 桌面的端口为 8000,在电脑浏览器中输入 “AidLux 设备的 IP 地址:8000”,如提示需要输入密码,该密码是 AidLux root 账户密码,默认密码是 “aidlux”。需注意,远程访问鉴权为 session 机制,每次关闭或重启 AidLux 均需重新输入密码进行访问。
- 使用 SSH 密码连接
- 查看被连接设备的 IP 地址:方法同上。
- 在电脑上打开终端:以 Windows 为例,可右键左下角 Windows 键打开 “Windows PowerShell(管理员)” 或以管理员方式打开 “cmd 命令提示符”;Mac 则使用 “终端” 或 “iTerm2” 等。
- 输入连接命令:输入 “ssh root@[AidLux 设备的 IP 地址] -p9022”,例如 “ssh root@192.168.110.63 -p9022”,然后根据提示输入密码(默认的 root 密码为 “aidlux”)。不过在一些较老的设备上可能无法通过密码方式进行 SSH 连接,连接时会提示 “Connection refused”,同时可能会导致 Aid 平台无法正常使用,重启即可恢复。
- 使用 SSH 密钥连接
- 在 PC 上生成公钥和私钥:以 Windows 为例,右键左下角 Windows 键打开 “Windows PowerShell(管理员)” 或以管理员方式打开 “cmd 命令提示符”。输入 “ssh -keygen” 命令,按提示操作即可生成密钥。生成的密钥默认放在用户目录下的.ssh 文件夹中。如果已经生成过密钥,则可以跳过该步骤。
- 上传公钥和私钥到 AidLux:打开浏览器,输入 “http://[AidLux 设备的 IP 地址]:8910/upload”,例如 “http://192.168.110.63:8910/upload”。点击 “选择文件” 按钮,先选择公钥点击上传,待上传成功后,再次点击 “选择文件” 按钮,选择私钥点击上传。注意需要分开上传私钥 “id_rsa” 和公钥 “id_rsa.pub” 文件,不能一次上传两个文件。
- 连接:打开 Windows 的 “PowerShell” 或者 “cmd 命令提示符”,输入 “ssh root@[AidLux 设备的 IP 地址] -p 8022”,例如 “ssh root@192.168.110.63 -p 8022”,根据提示进行连接即可。需注意,AidLux 版本 < 1.1 时,可能无法正常访问上传地址,需在 Aid 桌面的应用中心或 Aid Linux 终端使用 “aid install” 安装 “open - sshkey”,然后才能正常上传公钥和私钥。
- 通过 VScode 远程连接
- 安装 Remote - SSH 插件:在本地电脑的 VScode 中安装 “Remote - SSH” 插件。
- 配置 SSH 连接:点击 “Remote Explorer”,再点击左下角的 “Open a Remote Window”,选择 “Open SSH Configuration file”,针对跳出的弹窗,选择第一个 “config” 进行配置。配置内容如下:
- Host:可填写服务器别名,一般不需要改动。
- HostName:填写 AidLux 设备的 “cloud_ip” 地址。
- Port:填写 9022。
- User:填写 “root”,这是远程登录的用户名,一般默认即可。
- 连接 AidLux:保存配置后,在左侧框里会生成一个 SSH 服务器,鼠标放在上面,右侧会出现一个文件夹一样的图标,点击它,然后选择 “Linux”,点击 “Continue”,再输入密码 “aidlux”,回车。当左下角出现 “SSH AidLux” 时,表示与手机端连接成功。
四、进入 AidLux 的 Linux 系统
成功登录后,会弹出一个界面询问是否进行某些设置,直接点击 “否”。若点击 “是”,可能会进入一个僵持界面,无法进行后续操作。点击 “否” 后,即可进入 AidLux 的 Linux 系统桌面。
若不幸出现异常界面(通常在 Android 12 及以上系统可能出现),可尝试关闭 AidLux 应用后重新打开。这可能是由于系统设置问题导致 AidLux 进程被干扰,重新打开应用一般可解决该问题。
查看Linux的系统版本
lsb_release -a
五、AidLux 中 Python 编程的途径
(一)命令行模式
- 打开命令行:在 AidLux 桌面找到 “终端” 应用并打开。需要注意的是,在 “终端” 应用中输入 “python” 命令(注意是小写的 python),即可进入 Python 交互式编程环境。在此环境下,可逐行输入 Python 代码并立即查看运行结果,就如同在 Windows 系统下的 cmd 命令窗口操作一样。
- 命令行模式优势:命令行模式简洁高效,适合进行简单的代码测试和快速验证想法。例如,可直接在命令行中输入 “print ('Hello, Python!')” 来测试 Python 的基本输出功能。同时,在 “命令行模式” 应用中进行编程,不会出现网络无法连接的情况,能让开发者专注于代码编写,不过此模式下没有代码编辑器的高级功能,如代码自动补全、语法高亮等。
(二)自带编译器
- 编译器界面介绍:在 AidLux 桌面打开代码编辑应用(一般图标比较明显),该编译器界面简洁,易于上手。顶部为操作区域,底部为代码区域。
- 操作按钮功能:
- 点击顶部第一个按钮,将展开一个二级按钮菜单,其中 “Run Now” 用于运行当前代码,点击后编译器将执行底部代码区域中的 Python 代码,并在指定区域显示运行结果;“Stop” 用于停止正在运行的代码,当代码出现死循环或其他异常情况时,可点击此按钮终止程序运行。
- 点击顶部第二个按钮,同样展开一个二级按钮菜单,“Open” 用于打开已有的 Python 代码文件;“New” 可新建一个 Python 代码文件;“Save” 用于保存当前正在编辑的代码文件,在编写代码过程中,应适时点击保存,防止代码丢失。
- 点击顶部第三个按钮,可以查看最近打开的文件列表,方便快速切换和继续编辑之前的项目。
- 点击顶部第四个按钮,可以设置代码风格和文字大小,用户可根据个人喜好调整代码显示效果,使代码阅读起来更舒适。
(三)使用 VSCode(可选)
- 安装 VSCode:在 AidLux 桌面找到类似字母 “A” 的应用并打开,在应用列表中下滑或通过搜索找到 “vscode”,点击 “安装” 按钮,等待安装完成。安装过程所需时间取决于网络速度和手机性能。
- 设置工作路径:安装完成后,点击左下角的 “已安装”,找到安装好的 vscode,点击 “添加到桌面”。首先点击桌面下方任务栏第二个应用,进入终端。在终端中输入第一行命令 “cd /root/Desktop”,用于切换到桌面目录;再输入第二行命令 “mkdir pythonWorkFolder”,用于创建一个新的目录,作为 vscode 的工作路径。
- 打开 VSCode 并配置工作目录:点击桌面的 vscode 应用图标打开 vscode,在 vscode 界面中点击 “Open Folder”,选择或输入之前创建的路径 “/root/Desktop/pythonWorkFolder”,最后点击 “ok” 或按回车键,即可进入工作目录。在该工作目录下,可创建新的 Python 文件进行编程。创建.py 文件时,点击打开的工作目录 “PYTHONWORKFOLDER”(默认显示全大写),点击灰色圆圈●处的带 + 号的按钮,输入文件名字即可创建一个新的 Python 文件。
六、简单 Python 代码示例
在 AidLux 中使用 Python 进行编程时,可从一些简单的代码示例入手。
(一)简单的 Hello World 应用(带按钮)
import cv2
import numpy as np
# 创建空白图像
width, height = 400, 300
image = np.ones((height, width, 3), dtype=np.uint8) * 255 # 白色背景
# 文本和按钮属性
text = "Hello World!"
button_text = "Press me!"
button_color = (0, 120, 255) # 蓝色
text_color = (0, 0, 0) # 黑色
# 绘制初始文本
cv2.putText(image, text, (100, 100), cv2.FONT_HERSHEY_SIMPLEX, 1, text_color, 2)
# 按钮位置和尺寸
button_x, button_y = 100, 150
button_width, button_height = 200, 50
# 绘制按钮
cv2.rectangle(image, (button_x, button_y), (button_x + button_width, button_y + button_height), button_color, -1)
cv2.putText(image, button_text, (button_x + 50, button_y + 30), cv2.FONT_HERSHEY_SIMPLEX, 0.7, text_color, 2)
# 按钮点击状态
button_pressed = False
def mouse_callback(event, x, y, flags, param):
global button_pressed, image
# 检查鼠标点击是否在按钮区域内
if event == cv2.EVENT_LBUTTONDOWN:
if button_x <= x <= button_x + button_width and button_y <= y <= button_y + button_height:
button_pressed = not button_pressed
# 更新图像
image = np.ones((height, width, 3), dtype=np.uint8) * 255 # 重置背景
# 根据按钮状态更新文本
display_text = "Button pressed!" if button_pressed else text
cv2.putText(image, display_text, (100, 100), cv2.FONT_HERSHEY_SIMPLEX, 1, text_color, 2)
# 绘制按钮(状态可能改变)
cv2.rectangle(image, (button_x, button_y), (button_x + button_width, button_y + button_height),
button_color if not button_pressed else (0, 255, 0), -1)
cv2.putText(image, button_text, (button_x + 50, button_y + 30), cv2.FONT_HERSHEY_SIMPLEX, 0.7, text_color, 2)
# 创建窗口并设置鼠标回调
cv2.namedWindow("Hello World App")
cv2.setMouseCallback("Hello World App", mouse_callback)
# 主循环
while True:
cv2.imshow("Hello World App", image)
# 按ESC键退出
key = cv2.waitKey(1)
if key == 27: # ESC键
break
cv2.destroyAllWindows()
代码运行效果图:
因为有UI,因此需要在xfce的桌面环境中运行,如果没有UI可以在AidLux提供的web desktop中运行。
(二)计算器应用
import cv2
import numpy as np
# 创建空白图像
width, height = 400, 500
image = np.ones((height, width, 3), dtype=np.uint8) * 255 # 白色背景
# 计算器状态
display_text = "0"
buttons = []
button_size = 70
button_margin = 10
button_color = (0, 120, 255)
text_color = (0, 0, 0)
special_button_color = (255, 100, 100) # DEL和C按钮的颜色
# 按钮定义(行,列,标签)
button_layout = [
('7', 1, 0), ('8', 1, 1), ('9', 1, 2), ('/', 1, 3),
('4', 2, 0), ('5', 2, 1), ('6', 2, 2), ('*', 2, 3),
('1', 3, 0), ('2', 3, 1), ('3', 3, 2), ('-', 3, 3),
('0', 4, 0), ('.', 4, 1), ('=', 4, 2), ('+', 4, 3),
('DEL', 0, 2), ('C', 0, 3) # 添加删除键和清除键
]
# 创建按钮
for label, row, col in button_layout:
x = button_margin + col * (button_size + button_margin)
y = 100 + row * (button_size + button_margin)
buttons.append({
'label': label,
'x': x,
'y': y,
'width': button_size,
'height': button_size
})
def draw_calculator():
global image
image = np.ones((height, width, 3), dtype=np.uint8) * 255 # 重置背景
# 绘制显示区域
cv2.rectangle(image, (button_margin, button_margin),
(width - button_margin, 80), (220, 220, 220), -1)
cv2.putText(image, display_text, (20, 60), cv2.FONT_HERSHEY_SIMPLEX, 1.2, text_color, 2)
# 绘制按钮
for button in buttons:
x, y = button['x'], button['y']
w, h = button['width'], button['height']
# 特殊按钮使用不同颜色
if button['label'] in ['DEL', 'C']:
cv2.rectangle(image, (x, y), (x + w, y + h), special_button_color, -1)
else:
cv2.rectangle(image, (x, y), (x + w, y + h), button_color, -1)
cv2.putText(image, button['label'], (x + 25 if button['label'] != 'DEL' else x + 15, y + 45),
cv2.FONT_HERSHEY_SIMPLEX, 1, text_color, 2)
def mouse_callback(event, x, y, flags, param):
global display_text
if event == cv2.EVENT_LBUTTONDOWN:
for button in buttons:
bx, by = button['x'], button['y']
bw, bh = button['width'], button['height']
if bx <= x <= bx + bw and by <= y <= by + bh:
label = button['label']
if label == '=':
try:
result = eval(display_text)
display_text = str(result)
except:
display_text = "Error"
elif label == 'DEL':
# 实现回退删除功能
if len(display_text) > 1:
display_text = display_text[:-1]
else:
display_text = "0"
elif label == 'C':
# 实现清除功能
display_text = "0"
else:
if display_text == "0":
display_text = label
else:
display_text += label
draw_calculator()
# 初始化计算器显示
draw_calculator()
# 创建窗口并设置鼠标回调
cv2.namedWindow("Calculator")
cv2.setMouseCallback("Calculator", mouse_callback)
# 主循环
while True:
cv2.imshow("Calculator", image)
# 按ESC键退出
key = cv2.waitKey(1)
if key == 27: # ESC键
break
cv2.destroyAllWindows()
代码运行效果:
(三) 绘图应用
import cv2
import numpy as np
# 创建空白图像
width, height = 800, 600
image = np.ones((height, width, 3), dtype=np.uint8) * 255 # 白色背景
# 绘图状态
drawing = False
last_x, last_y = 0, 0
color = (0, 0, 0) # 黑色
size = 2
# 颜色选项
colors = {
'black': (0, 0, 0),
'red': (0, 0, 255),
'green': (0, 255, 0),
'blue': (255, 0, 0),
'yellow': (0, 255, 255)
}
# 尺寸选项
sizes = [1, 2, 5, 10]
# 工具栏高度
toolbar_height = 50
def draw_toolbar():
# 绘制工具栏背景
cv2.rectangle(image, (0, 0), (width, toolbar_height), (200, 200, 200), -1)
# 绘制颜色按钮
x = 10
for name, rgb in colors.items():
bgr = (rgb[2], rgb[1], rgb[0]) # OpenCV使用BGR顺序
cv2.rectangle(image, (x, 10), (x + 30, 40), bgr, -1)
if bgr == color: # 当前选中的颜色
cv2.rectangle(image, (x, 10), (x + 30, 40), (0, 0, 0), 2)
x += 40
# 绘制尺寸按钮
x += 20
for s in sizes:
cv2.rectangle(image, (x, 10), (x + 30, 40), (100, 100, 100), -1)
cv2.putText(image, str(s), (x + 10, 30), cv2.FONT_HERSHEY_SIMPLEX, 0.5, (0, 0, 0), 1)
if s == size: # 当前选中的尺寸
cv2.rectangle(image, (x, 10), (x + 30, 40), (0, 0, 0), 2)
x += 40
def mouse_callback(event, x, y, flags, param):
global drawing, last_x, last_y, color, size
if y < toolbar_height: # 点击工具栏
if event == cv2.EVENT_LBUTTONDOWN:
# 检查颜色按钮
color_x = 10
for name, rgb in colors.items():
if color_x <= x <= color_x + 30:
color = (rgb[2], rgb[1], rgb[0]) # OpenCV使用BGR顺序
draw_toolbar()
break
color_x += 40
# 检查尺寸按钮
size_x = color_x + 20
for s in sizes:
if size_x <= x <= size_x + 30:
size = s
draw_toolbar()
break
size_x += 40
else: # 绘图区域
if event == cv2.EVENT_LBUTTONDOWN:
drawing = True
last_x, last_y = x, y
elif event == cv2.EVENT_MOUSEMOVE:
if drawing:
cv2.line(image, (last_x, last_y), (x, y), color, size)
last_x, last_y = x, y
elif event == cv2.EVENT_LBUTTONUP:
drawing = False
cv2.line(image, (last_x, last_y), (x, y), color, size)
# 初始化界面
draw_toolbar()
# 创建窗口并设置鼠标回调
cv2.namedWindow("Drawing App")
cv2.setMouseCallback("Drawing App", mouse_callback)
# 主循环
while True:
cv2.imshow("Drawing App", image)
# 按ESC键退出
key = cv2.waitKey(1)
if key == 27: # ESC键
break
cv2.destroyAllWindows()
示例效果:
(四)待办事项应用
import cv2
import numpy as np
# 创建空白图像
width, height = 600, 500
image = np.ones((height, width, 3), dtype=np.uint8) * 255 # 白色背景
# 待办事项列表
tasks = []
task_input = ""
show_keyboard = False
# 字体和颜色设置
font = cv2.FONT_HERSHEY_SIMPLEX
text_color = (0, 0, 0)
button_color = (0, 120, 255)
task_bg_color = (220, 220, 220)
# 按钮和输入框位置
add_button = {'x': 500, 'y': 50, 'width': 80, 'height': 30}
input_box = {'x': 20, 'y': 50, 'width': 460, 'height': 30}
def draw_todo_app():
global image
image = np.ones((height, width, 3), dtype=np.uint8) * 255 # 重置背景
# 绘制标题
cv2.putText(image, "Todo List", (20, 30), font, 1, text_color, 2)
# 绘制输入框
cv2.rectangle(image, (input_box['x'], input_box['y']),
(input_box['x'] + input_box['width'], input_box['y'] + input_box['height']),
(200, 200, 200), -1)
cv2.putText(image, task_input, (input_box['x'] + 10, input_box['y'] + 20), font, 0.5, text_color, 1)
# 绘制添加按钮
cv2.rectangle(image, (add_button['x'], add_button['y']),
(add_button['x'] + add_button['width'], add_button['y'] + add_button['height']),
button_color, -1)
cv2.putText(image, "Add", (add_button['x'] + 25, add_button['y'] + 20), font, 0.5, text_color, 1)
# 绘制任务列表
for i, task in enumerate(tasks):
y_pos = 100 + i * 40
cv2.rectangle(image, (20, y_pos), (width - 20, y_pos + 30), task_bg_color, -1)
# 任务文本
cv2.putText(image, task['text'], (30, y_pos + 20), font, 0.5, text_color, 1)
# 删除按钮
delete_btn = {'x': width - 60, 'y': y_pos, 'width': 40, 'height': 30}
cv2.rectangle(image, (delete_btn['x'], delete_btn['y']),
(delete_btn['x'] + delete_btn['width'], delete_btn['y'] + delete_btn['height']),
(0, 0, 255), -1)
cv2.putText(image, "X", (delete_btn['x'] + 15, delete_btn['y'] + 20), font, 0.5, (255, 255, 255), 1)
# 保存按钮位置供点击检测
task['delete_btn'] = delete_btn
def mouse_callback(event, x, y, flags, param):
global tasks, task_input, show_keyboard
if event == cv2.EVENT_LBUTTONDOWN:
# 检查是否点击添加按钮
if (add_button['x'] <= x <= add_button['x'] + add_button['width'] and
add_button['y'] <= y <= add_button['y'] + add_button['height']):
if task_input.strip():
tasks.append({'text': task_input, 'completed': False})
task_input = ""
draw_todo_app()
# 检查是否点击删除按钮
for task in tasks[:]: # 使用副本避免迭代时修改列表
btn = task['delete_btn']
if btn['x'] <= x <= btn['x'] + btn['width'] and btn['y'] <= y <= btn['y'] + btn['height']:
tasks.remove(task)
draw_todo_app()
break
# 初始化应用
draw_todo_app()
# 创建窗口并设置鼠标回调
cv2.namedWindow("Todo App")
cv2.setMouseCallback("Todo App", mouse_callback)
# 主循环
while True:
cv2.imshow("Todo App", image)
# 处理键盘输入
key = cv2.waitKey(1) & 0xFF
if key == 27: # ESC键退出
break
elif key == 13: # Enter键添加任务
if task_input.strip():
tasks.append({'text': task_input, 'completed': False})
task_input = ""
draw_todo_app()
elif key == 8: # Backspace键删除字符
task_input = task_input[:-1]
draw_todo_app()
elif key >= 32 and key <= 126: # 可打印字符
task_input += chr(key)
draw_todo_app()
cv2.destroyAllWindows()
示例图:
(五)高通手机跑AI系列之——468个面部关键点提取
(六)高通手机跑AI系列之——人像与背景分割-CSDN博客
(七) 高通手机跑AI系列之——人像与背景分割-CSDN博客
(八)高通手机跑AI系列之——实时头发识别-CSDN博客
(九)高通手机跑AI系列之——姿态识别-CSDN博客
七、常见问题及解决方法
(一)AidLux 服务进程被杀死(Android 12 及以上系统)
- 问题原因:Android 12 及更新版本增加了一种机制,会监视应用程序启动的分支子进程(虚进程),若发现其运行数量超过默认的 32 个(针对所有应用程序启动的分支子进程之和),则会杀死它们。HarmonyOS 3 由于使用的 Android 版本提升到了 12,也引入了此特性,这可能导致 AidLux 服务进程被意外终止。
- 解决方法:虽然目前没有完全根治的办法,但可通过一些措施尽量减少进程被杀死的概率。一是提高手机性能,打开手机的电池性能模式,同时多进入多窗口模型,巡查并关闭其他不必要的多开应用进程,减少挂着但不使用的进程,为 AidLux 运行提供更稳定的环境。二是设置 AidLux 默认后台运行(但此方法十分耗电)。具体操作如下:
- 点击手机 “设置” - “应用和服务” - “应用启动管理”,将 AidLux 设置为手动管理,同时打开 “允许自启动”“允许管理启动”“允许后台运行”。
- 进入手机 “设置” - “电池” - “更多电池设置”,打开 “休眠时始终保持网络连接”。
(二)输入法问题
建议使用手机系统自带的输入法。
(三)文件操作权限问题
在 AidLux 中,只有 “/home/AidLux” 目录有权限接受文件上传。若在进行文件上传等操作时遇到权限不足的提示,应确保将文件上传至该目录或其下属有权限的子目录中。同时,在使用文件浏览器进行新建文件夹、新建文件等操作时,若操作失败,也可能是权限问题,可检查当前操作目录是否有权限执行相应操作。
提示:AidLux环境中文件系统(home)有一个好处就是其他Android app无法访问,通过拖拽就能把电脑端的文件复制到手机中,而且只有输入了你的账号和密才能从AidLux入口访问,也是妥妥的隐私保护神器。