首页 > 其他分享 >53.收官 Android四大组件之一服务

53.收官 Android四大组件之一服务

时间:2024-06-18 09:43:40浏览次数:25  
标签:服务 53 public Override Intent 组件 import Android android

服务 一个长期运行在后台的用户组件 不依赖于Activity

只有当系统必须回收内存资源时 才会被销毁

首先是创建服务
image

当写好后 会自动在清单文件中注册

image

服务的生命周期和启动方式

先简单介绍一下 然后用两个小案例来日志打印验证

第一种启动方式 startService()

image
启动服务的组件和服务之间没有关联 组件销毁 服务依旧运行

验证下:
package com.example.service;

import android.app.Service;
import android.content.Intent;
import android.os.IBinder;
import android.util.Log;

public class TestService extends Service {
    public TestService() {
    }

    @Override
    public void onCreate() {
        super.onCreate();
        Log.i("文雅", "创建服务 onCreate()执行");
    }

    @Override
    public int onStartCommand(Intent intent, int flags, int startId) {
        Log.i("文雅", "开启服务 onStartCommand()执行");
        return super.onStartCommand(intent, flags, startId);

    }

	//此处为第一种启动方式
    @Override
    public IBinder onBind(Intent intent) {
        return null;
    }

    @Override
    public void onDestroy() {
        super.onDestroy();
        Log.i("文雅", "关闭服务 onDestroy()执行");

    }
}
package com.example.service;

import android.content.Intent;
import android.view.View;
import android.widget.Button;

import androidx.appcompat.app.AppCompatActivity;

public class ToServiceActivity extends AppCompatActivity {
    @Override
    protected void onStart() {
        super.onStart();
        setContentView(R.layout.activity_toservice);
        Button bt1 = findViewById(R.id.bt1);
        Button bt2 = findViewById(R.id.bt2);
        Intent testService = new Intent(this, TestService.class);

        bt1.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                startService(testService);
            }
        });

        bt2.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                stopService(testService);
            }
        });
    }
}

第一次启动服务
image
关闭Activity 打开 服务直接启动
image
关闭服务
image


第二种启动方式 bindService()

image
组件绑定服务 解绑服务 服务即销毁 多个组件可绑定一个服务

             * 第一个参数 指定启动的Service
             * 第二个参数 调用者与Service之间的连接状态
             * 第三个参数 绑定服务时是否自动创建Service
            bindService(intent, myconn, BIND_AUTO_CREATE);
package com.example.service;

import android.app.Service;
import android.content.Intent;
import android.os.Binder;
import android.os.IBinder;
import android.util.Log;

public class MyBindService extends Service {
    public MyBindService() {
    }

    class MyBinder extends Binder {
        public void callMethod() {
            method();
        }
    }

    @Override
    public void onCreate() {
        super.onCreate();
        Log.i("芳芳", "创建服务 执行onCreate()方法");
    }

    @Override
    public IBinder onBind(Intent intent) {
        Log.i("芳芳", "绑定服务 执行onBind()方法");
        return new MyBinder();

    }

    public void method() {
        Log.i("芳芳", "调用服务中的method()方法");
    }

    @Override
    public boolean onUnbind(Intent intent) {
        Log.i("芳芳", "解绑服务 执行onUnbind()方法");
        return super.onUnbind(intent);

    }
}
package com.example.service;

import android.annotation.SuppressLint;

import android.content.ComponentName;
import android.content.Intent;
import android.content.ServiceConnection;
import android.os.IBinder;
import android.util.Log;
import android.view.View;
import android.widget.Button;

import androidx.appcompat.app.AppCompatActivity;

public class BindServiceActivity extends AppCompatActivity implements View.OnClickListener {
    private Button btt1, btt2, btt3;
    private Myconn myconn;
    private MyBindService.MyBinder myBinder;
// @SuppressLint("MissingInflatedId") 是一个 Android Lint 注解,用于告诉 Lint 工具忽略某个特定的警告
    @SuppressLint("MissingInflatedId")
    @Override
    protected void onStart() {
        super.onStart();
        setContentView(R.layout.activity_bindservice);
        btt1 = findViewById(R.id.btt1);
        btt2 = findViewById(R.id.btt2);
        btt3 = findViewById(R.id.btt3);

        btt1.setOnClickListener(this);
        btt2.setOnClickListener(this);
        btt3.setOnClickListener(this);


    }

    @Override
    public void onClick(View v) {
        //绑定服务
        if (v.getId() == R.id.btt1) {
            if (myconn == null) {
                myconn = new Myconn();
            }
            Intent intent = new Intent(this, MyBindService.class);
            /**
             * 第一个参数 指定启动的Service
             * 第二个参数 调用者与Service之间的连接状态
             * 第三个参数 绑定服务时是否自动创建Service
             */
            bindService(intent, myconn, BIND_AUTO_CREATE);
        }
        //调用服务中的方法
        if (v.getId() == R.id.btt2) {
            myBinder.callMethod();
        }
        //解绑服务
        if (v.getId() == R.id.btt3) {
            if (myconn != null) {
                unbindService(myconn);
                myconn = null;
            }

        }


    }

    //bindService第二个参数 实现连接服务
    private class Myconn implements ServiceConnection {

        // 成功绑定时 调用onServiceConnected()方法
        // 失去连接时 调用onServiceDisconnected()方法
        @Override
        public void onServiceConnected(ComponentName name, IBinder service) {
            myBinder = (MyBindService.MyBinder) service;
            Log.i("芳芳", "服务成功绑定");
        }

        @Override
        public void onServiceDisconnected(ComponentName name) {
        }
    }
}

不能直接调用方法 必须在成功绑定后才能调用
image
绑定服务
image
调用方法
image
解绑服务
image

关于直接调用methon()方法 AI给出答复:

类型安全:onServiceConnected 方法接收一个 IBinder 类型的参数。尽管您知道这个 IBinder 实际上是 MyBinder 的一个实例,但编译器并不知道这一点。因此,您需要通过强制类型转换来将其转换为 MyBinder 类型,然后才能调用 callMethod() 方法。

访问权限:method() 方法是 MyBindService 类的一个公共方法,但它不是 IBinder 接口的一部分。因此,没有 MyBinder 作为中介,您无法直接访问它。

设计模式:使用 Binder 类是 Android 服务绑定的一种常见设计模式。它允许您定义特定的方法来与服务交互,而不是直接访问服务的所有公共方法。这有助于封装和抽象,使代码更加清晰和可维护。

标签:服务,53,public,Override,Intent,组件,import,Android,android
From: https://www.cnblogs.com/gaodiyuanjin/p/18253676

相关文章

  • 52.Android四大名捕之一...四大组件之一广播
    广播(Broadcast)啥叫广播例如:电池电量低的时候会提醒电量不足这就是广播广播即在组件之间传递消息的机制Binder机制Binder机制作为Android系统中非常重要的一部分,为不同进程之间的数据共享和通信提供了高效、稳定的解决方案。开发者在Android开发中,可以通过Android提供的Bi......
  • Unity中使用UI组件实现场景切换——6.18山大软院项目实训
    设置场景切换在Unity项目中,首先需要准备几个场景,并在项目的“BuildSettings”中添加这些场景,以确保SceneManager可以加载它们。本例中,我们假设已有几个场景编号依次为1到5。脚本概述我们创建了一个SwitchScene类,这个类包含了几个公共方法,允许通过不同方式切换场景:使用下拉......
  • 【Vue3的组合式API】超详细教程,含computed、watch、组件通信、模版引用......
    前言:哈喽,大家好,我是前端菜鸟的自我修养!今天给大家分享【Vue3的组合式API】超详细教程,包含setup语法糖、computed、watch、组件通信、模版引用、vue3新特性等等......,并提供具体代码帮助大家深入理解,彻底掌握!原创不易,如果能帮助到带大家,欢迎收藏+关注哦......
  • LVGL btn组件
    /***************************************************filename:widget_line.c*author:[email protected]*date:2024/06/17*brief:移植LVGL,实现在屏幕上显示一个按钮,按钮上有一个标签,当用户通过触摸屏点击了该按钮,则显示一个新的屏幕对象*not......
  • Android 11 禁止从SD卡上安装第三方应用
    找到负责安装app的类:./frameworks/base/services/core/java/com/android/server/pm/PackageManagerService.java修改日志变量,打印日志,顺着日志看流程:publicstaticfinalbooleanDEBUG_INSTALL=true;05-2809:12:12.46241234184IPackageManager:init_copy:Install......
  • ABC353F 分讨
    回来补补题。分析:我先考虑\(k\)很大的时候,大块和大块间的移动,我们不得不尽量避免小块:我们容易发现这样时是最优的,可以发现就是在斜着走,也就是典型的切比雪夫距离。斜着走一次需要经过两条边,所以花费是两倍的切比雪夫距离。要是起点和终点不在大块上呢?首先考虑它们不在同一......
  • 谈一谈Android系统和iOS系统的点击实现复制功能
    序言:   谈到复制功能,想必大多数人都使用的navigator.clipboard.writeText()来实现对文本的复制。但是这个方法却只能在Android系统中成功复制到剪切板,在iOS系统中却不行,下面就谈谈iOS系统中的问题和实现方法。问题描述:iOS对用户数据和设备功能的访问有着严格的控制,尤其是......
  • Android 屏幕适配
    目录一、目的二、环境三、相关概念3.1屏幕尺寸(screensize)3.2屏幕分辨率(Resolution)3.3像素(pixel)3.4ppi3.5dpi3.6dp/dip3.7sp四、Q&A4.1为啥dpi=160?4.2为啥Android要引入dp概念?五、代码仓库地址六、参考资料一、目的        最近在调试一款设备,发现视......
  • React中AntDesign upload组件 自定义请求将多个上传请求合并成一个并
    接口文档核心代码constImportPictureUpload=()=>{const[fileList,setFileList]=useState([])constonBeforeUpload=(file:any,fileList:any)=>{setFileList(fileList)returnfalse;}useEffect(()=>{if(......
  • Ant Design Vue 的 Notification 组件如何调用以及常见问题解释
    AntDesignVue是一个基于Vue.js的UI组件库,它提供了一套丰富的组件来构建高质量的企业级应用程序。其中,Notification组件用于在屏幕的角落显示全局通知,以告知用户某些信息或操作的结果。以下是关于如何在AntDesignVue中调用Notification组件的详细介绍。什么是......