首页 > 分享 > 在安卓上实现一个桌面宠物APP

在安卓上实现一个桌面宠物APP

2021-01-14

1 桌面宠物APP需求分析

1.1 项目简介

使用安卓开发实现一个类似QQ宠物的桌面宠物APP。

1.2 灵感来源

之前看到360安全卫士在安卓桌面实现悬浮窗的功能,我想利用悬浮窗这个想法来实现一个全局安卓桌面宠物APP。

1.3 实现功能

• 宠物成长功能:根据手机使用时长实现宠物进化升级的功能,主要是宠物形态的变化;
• 随意移动宠物;
• 点击宠物打开功能菜单:包括照相、购物和回家功能;
• 打开APP首页;
• 打开淘宝首页;
• 打开照相机;
• 未完待续。

2 桌面宠物APP实现分析

2.1 悬浮窗的实现

基于Android开发四大组件之一的Service实现悬浮窗。
• 定义PetWindowService类继承Service类

1

public class PetWindowService extends Service{...}

• 用WindowManager类来实现悬浮窗的窗体参数的设置。

1

wm = (WindowManager) getSystemService(Context.WINDOW_SERVICE);

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32

private void showPetView() {
//获取屏幕宽度和高度
winWidth = wm.getDefaultDisplay().getWidth();
winHeight = wm.getDefaultDisplay().getHeight();
params = new WindowManager.LayoutParams();

int LAYOUT_FLAG;
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
LAYOUT_FLAG = WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY;
} else {
LAYOUT_FLAG = WindowManager.LayoutParams.TYPE_SYSTEM_ALERT;
}
// 自定义宠物窗体params.height = WindowManager.LayoutParams.WRAP_CONTENT;
params.width = WindowManager.LayoutParams.WRAP_CONTENT;
// 屏幕左上角对齐
params.gravity = Gravity.LEFT + Gravity.TOP;
params.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE
| WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON;
params.format = PixelFormat.TRANSLUCENT;
params.type = LAYOUT_FLAG;

// 加入宠物窗体
petView = View.inflate(this, R.layout.activity_pet, null);
// 悬浮窗功能菜单控件
imageView = petView.findViewById(R.id.petView);
imgHome = petView.findViewById(R.id.imgHome);
imgCart = petView.findViewById(R.id.imgCart);
imgCamera = petView.findViewById(R.id.imgCamera);
petNameView = petView.findViewById(R.id.petName);

wm.addView(petView, params);
}

• 实现宠物拖拽。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48

// 实现拖拽宠物
imageView.setOnTouchListener(new View.OnTouchListener() {
@Override
public boolean onTouch(View v, MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:

startX = (int) event.getRawX();
startY = (int) event.getRawY();
break;

case MotionEvent.ACTION_MOVE:
int moveX = (int) event.getRawX();
int moveY = (int) event.getRawY();

int disX = moveX - startX;
int disY = moveY - startY;

params.x = params.x + disX;
params.y = params.y + disY;

if (params.x < 0) {
params.x = 0;
}

if (params.y < 0) {
params.y = 0;
}

if (params.x > winWidth - petView.getWidth()) {
params.x = winWidth - petView.getWidth();
}

if (params.y > winHeight - petView.getHeight()) {
params.y = winHeight - petView.getHeight();
}

wm.updateViewLayout(petView, params);

startX = (int) event.getRawX();
startY = (int) event.getRawY();
break;
case MotionEvent.ACTION_UP:
break;
}
return false;
}
});

2.2 宠物功能菜单栏的实现

• 实现功能菜单栏,主要是ImageView的监听事件
实现菜单开关:使用count计数来判断奇数单击还是偶数单击对应打开菜单和关闭菜单。
控制菜单可见方法:ImageView控件的setVisibility方法包括三个属性:VISIBLE、GONE、INVISIBLE,分别表示控件可见、不可见且不占位、不可见且占位。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18

// 实现单击打开菜单,第二次关闭菜单
imageView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
count++;
if(count % 2 == 1){
imgHome.setVisibility(View.VISIBLE);
imgCamera.setVisibility(View.VISIBLE);
imgCart.setVisibility(View.VISIBLE);
}
else {
imgHome.setVisibility(View.GONE);
imgCamera.setVisibility(View.GONE);
imgCart.setVisibility(View.GONE);
count = 0;
}
}
});

• 跳转到APP主页,从Service跳转到Activity需要设置intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);,跳转到其他APP也要用到这行代码。

1
2
3
4
5
6
7
8
9

// 点击imgHome打开主页面
imgHome.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent intent = new Intent(PetWindowService.this, MainActivity.class);
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(intent);
}
});

• 跳转到相机。

1
2
3
4
5
6
7
8
9
10

// 点击imgCamera打开相机
imgCamera.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent intent = new Intent();
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
intent.setAction("android.media.action.STILL_IMAGE_CAMERA");
startActivity(intent);
}
});

• 跳转到淘宝。

1
2
3
4
5
6
7
8
9
10
11

// 点击imgCart打开淘宝
imgCart.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent intent = new Intent();
intent.setAction("Android.intent.action.VIEW");
intent.setClassName("com.taobao.taobao", "com.taobao.tao.welcome.Welcome");
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(intent);
}
});

2.3 APP主页显示宠物信息

主页实现功能主要包括:宠物取名,选择宠物类型,领养新宠物,选择已有宠物进行展示,宠物名字展示,宠物类型展示,宠物年龄展示,释放宠物,收回宠物,删除宠物。
• 第一部分:创建宠物
选择宠物类型,Spinner控件监听事件。

1
2
3
4
5
6
7
8
9
10
11

// 选择宠物类型
petMode.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() {
@Override
public void onItemSelected(AdapterView<?> parent, View view, int position, long id) {
mode = modeArray[position];
}
@Override
public void onNothingSelected(AdapterView<?> parent) {

}
});

创建宠物类型,Button控件监听事件,将宠物名字一并记录。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31

// 创建宠物
bn_createPet.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {

// 取名
petName = editName.getText().toString();

boolean sameName = false;

for (int i = 0; i < petNameAdapter.getCount(); i++) {
if (petName.equals(petNameAdapter.getItem(i))) {
sameName = true;
break;
}
}

if (!editName.getText().toString().equals("") && !sameName){

// 创建宠物
createPet(mode, petName, petAgeSeconds);
Toast.makeText(MainActivity.this,
"恭喜你拥有了一只" + mode + "类宠物," + "它的名字叫" + petName,
Toast.LENGTH_LONG).show();
petNameAdapter.add(petName);

} else {
Toast.makeText(MainActivity.this, "名字不能为空或重复,请再次输入!", Toast.LENGTH_LONG).show();
}
}
});

• 第二部分:展示宠物信息
首先从数据库中选择已有宠物进行展示。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27

// 从数据库中选择一只宠物
petNameList.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() {
@Override
public void onItemSelected(AdapterView<?> parent, View view, int position, long id) {
tmp_name = (String) petNameList.getSelectedItem();
// 上一个宠物名字
if (!last_name.equals("")){
last_name = showPetName.getText().toString();
} else {
last_name = tmp_name;
}
// 显示宠物名字
showPetName.setText(tmp_name);
// 显示宠物类型
showPetMode.setText(getPetMode(tmp_name));
// 显示宠物图像
showPetImg.setImageResource(changePet(showPetMode.getText().toString()));
// 显示宠物年龄
petAgeView.setText(showPetAge(getPetAge(tmp_name)));

}

@Override
public void onNothingSelected(AdapterView<?> parent) {

}
});

释放宠物,即生成悬浮窗。

1
2
3
4
5
6
7
8
9
10
11
12
13
14

// 释放宠物
bn_showPet.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
// 传宠物参数到Service
Intent intent = new Intent(MainActivity.this, PetWindowService.class);
intent.putExtra("pet_name", showPetName.getText().toString())
.putExtra("pet_mode", showPetMode.getText().toString())
.putExtra("pet_age", String.valueOf(getPetAge(showPetName.getText().toString())));
startService(intent);
// finish();
Log.d(TAG, "onClick: 成功释放");
}
});

收回宠物。

1
2
3
4
5
6
7
8

// 收回宠物
bn_backPet.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent intent = new Intent(MainActivity.this, PetWindowService.class);
stopService(intent);
}
});

删除宠物:删除适配器和数据库对应宠物。

1
2
3
4
5
6
7

public void removePet(String name) {

// 删除适配器对应宠物对象
petNameAdapter.remove(name);
// 删除数据库对应宠物数据
usePetDB.removePet(name);
}

详细代码见github。

相关知识

在安卓上实现一个桌面宠物APP
桌面宠物安卓版app软件下载
逗鹅桌面宠物app安卓版下载
桌面宠物app哪个好?手机桌面宠物软件
互动桌面宠物(桌面宠物魔道祖师)V1.2 安卓免费版 V1.2安卓版
趣味萌宠app安卓版
激萌猫咪桌面宠物(咪萌桌面宠物)app安卓版
安卓桌面小宠物软件下载
咪萌桌面宠物免费安卓下载
哈屏宠物APP安卓版下载

网址: 在安卓上实现一个桌面宠物APP https://m.mcbbbk.com/newsview1131851.html

所属分类:萌宠日常
上一篇: 珠海·2023宠物展览会
下一篇: 宠物界新宠——弹窗UI设计,如何