Android中的Service(案例+代码+效果)

目录

Service概述

1.服务的主要特点

2.服务的类型

1)Started Service (启动服务)

2)Bound Service (绑定服务)

3)Foreground Service (前台服务)

3.服务的生命周期

onCreate()

onStartCommand(Intent, int, int)

onBind(Intent)

onUnbind(Intent)

onRebind(Intent)

onDestroy()

4.创建和使用服务

1--定义服务

2--在 Manifest 文件中声明服务

3--启动服务

4--绑定服务

5--注意事项

案例:Service的简单使用

1)创建一个服务

2)服务相关的操作

1---通过意图启动服务

2---通过意图关闭服务

3--创建服务连接类

4--绑定服务

5--解绑服务

6--调用服务方法

3)activity_main布局文件的编写

4)colors.xml文件

5)MainActivity代码

6)效果图


Service概述

在 Android 中,服务(Service)是一种可以在后台执行长时间运行操作的组件。与 Activity 不同,服务不提供用户界面,但可以保持应用程序的后台进程活跃,即使用户切换到其他应用或屏幕关闭时也能继续运行。以下是服务的一些关键概述:

1.服务的主要特点

  • 无用户界面:服务没有可见的用户界面,它在后台运行
  • 长时间运行:服务适合执行需要长时间运行的任务,如音乐播放、文件下载等。
  • 生命周期管理:服务有其自己的生命周期,可以通过 onCreate()onStartCommand()onBind()onUnbind(), 和 onDestroy() 等方法来管理。

2.服务的类型

1)Started Service (启动服务)

  • 通过 startService() 方法启动。
  • 一旦启动,服务将持续运行直到调用 stopSelf() 或 stopService()
  • 适用于不需要与启动它的组件保持交互的任务。

2)Bound Service (绑定服务)

  • 通过 bindService() 方法绑定到客户端。

  • 一旦绑定,客户端可以通过 IBinder 接口与服务进行交互。
  • 适用于需要频繁交互的情况,例如获取服务中的数据或控制服务的行为。

3)Foreground Service (前台服务)

  • 是一种特殊的服务,必须显示一个持续的通知给用户。
  • 前台服务不容易被系统杀死,适合执行重要且用户可见的任务。
  • 从 Android 8.0 (API 级别 26) 开始,如果一个服务在后台运行超过一定时间,它会被系统停止,除非它是前台服务。

3.服务的生命周期

  • onCreate()

    • 当服务第一次创建时调用。初始化设置在这里完成。
  • onStartCommand(Intent, int, int)

    • 每次通过 startService() 启动服务时调用。返回值决定服务如何处理重启情况。
  • onBind(Intent)

    • 当其他组件尝试通过 bindService() 绑定到服务时调用。返回一个 IBinder 对象以允许客户端与服务通信。
  • onUnbind(Intent)

    • 当最后一个客户端解除绑定时调用。
  • onRebind(Intent)

    • 当新的客户端试图绑定到服务时调用,前提是之前所有的客户端都已解除绑定。
  • onDestroy()

    • 在服务被销毁前调用,用于清理资源。

4.创建和使用服务

1--定义服务

public class MyService extends Service {
    @Override
    public void onCreate() {
        super.onCreate();
        // 初始化代码
    }

    @Override
    public int onStartCommand(Intent intent, int flags, int startId) {
        // 执行任务
        return START_STICKY; // 返回 START_STICKY 表示如果服务被意外终止,系统会尝试重启它
    }

    @Nullable
    @Override
    public IBinder onBind(Intent intent) {
        // 返回一个 IBinder 实例,用于与服务交互
        return null; // 如果不支持绑定,则返回 null
    }

    @Override
    public void onDestroy() {
        super.onDestroy();
        // 清理资源
    }
}

2--在 Manifest 文件中声明服务

<service android:name=".MyService" />

3--启动服务

Intent serviceIntent = new Intent(this, MyService.class);
startService(serviceIntent);

4--绑定服务

Intent serviceIntent = new Intent(this, MyService.class);
bindService(serviceIntent, connection, Context.BIND_AUTO_CREATE);

// ServiceConnection 实现
private ServiceConnection connection = new ServiceConnection() {
    @Override
    public void onServiceConnected(ComponentName name, IBinder service) {
        // 与服务建立连接后的操作
    }

    @Override
    public void onServiceDisconnected(ComponentName name) {
        // 服务断开连接后的操作
    }
};

5--注意事项

  • 性能和电池寿命:长时间运行的服务可能会消耗大量资源并影响电池寿命。因此,应该尽量减少后台服务的使用,并考虑使用 WorkManager 来替代一些后台任务。
  • 权限:某些服务可能需要特定的权限才能执行,比如访问网络。
  • 前台服务通知:从 Android 8.0 (API 级别 26) 开始,如果一个服务在后台运行超过一定时间,它会被系统停止,除非它是前台服务。前台服务必须显示一个持续的通知给用户。

        服务是 Android 应用程序架构中的一个重要部分,合理地使用它们可以帮助你构建出更加高效和响应迅速的应用程序。

案例:Service的简单使用

1)创建一个服务

鼠标右键包名===>new ===>Service===>Service

package com.xiji.myservice;

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

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

    //绑定服务的时候调用
    @Override
    public IBinder onBind(Intent intent) {
        System.out.println("MyService onBind");
        Log.i("MyService", "onBind");
        return null;
    }
    
    //解绑服务
    @Override
    public boolean onUnbind(Intent intent) {
        System.out.println("MyService onUnbind");
        Log.i("MyService", "onUnbind");
        return super.onUnbind(intent);
    }

    @Override
    public void onCreate() {
        super.onCreate();
        System.out.println("MyService onCreate");
        Log.i("MyService", "onCreate");
    }

    @Override
    public void onDestroy() {
        super.onDestroy();
        System.out.println("MyService onDestroy");
        Log.i("MyService", "onDestroy");
    }
    
    //Service代理类
    class MyServiceProxy extends Binder {
        public void userMyServiceMethods()
        {
            System.out.println("MyServiceProxy start");
            Log.i("MyService", "start");
            useServiceMethods();
        }
        
    }
    //服务里面的方法
    public void useServiceMethods() {
        System.out.println("MyService userMyServiceMethods");
        Log.i("MyService", "userMyServiceMethods");
    }
    
}

2)服务相关的操作

1---通过意图启动服务

//启动服务
public void startService() {
    //通过意图启动服务
    Intent intent = new Intent(this, MyService.class);
    
    startService(intent);


}

2---通过意图关闭服务

//关闭服务
public void stopService() {
    //通过意图关闭服务
    Intent intent = new Intent(this, MyService.class);
    stopService(intent);

}

3--创建服务连接类

创建服务连接类并且继承ServiceConnection

    //服务连接类
    private class MyServiceConnection implements ServiceConnection {
        @Override
        public void onServiceConnected(ComponentName name, IBinder service) {
            //连接服务时为其中的方法赋值
            myBinder = (MyService.MyServiceProxy) service;

            Log.i("MyService", "onServiceConnected连接服务" + service.toString());
        }

        @Override
        public void onServiceDisconnected(ComponentName name) {

        }
    }

4--绑定服务

使用bindService绑定服务

    //绑定服务
    public void bindMyService() {
        Intent intent = new Intent(this, MyService.class);
        //没有绑定服务时才绑定服务连接
        if (myServiceConnection == null) {
            //创建服务并且绑定
            myServiceConnection = new MyServiceConnection();
            //绑定服务
            bindService(intent, myServiceConnection, BIND_AUTO_CREATE);
            Toast.makeText(this, "绑定服务", Toast.LENGTH_SHORT).show();
            Log.i("MyService", "绑定服务");
            return ;
        }
        Toast.makeText(this, "服务已经连接", Toast.LENGTH_SHORT).show();


    }

5--解绑服务

使用unbindService解绑服务


    //解绑服务
    public void unBindMyService() {

        //有服务连接时才解绑
        if (myServiceConnection != null) {
            unbindService(myServiceConnection);
            Toast.makeText(this, "解绑服务", Toast.LENGTH_SHORT).show();
            Log.i("MyService", "解绑服务");
            myServiceConnection = null;
            //服务代理重置为空,不然还能使用
            if (myBinder != null) {
                myBinder = null;
                Toast.makeText(this, "服务代理重置为空", Toast.LENGTH_SHORT).show();
            }
            return ;
        }
        Toast.makeText(this, "服务未连接", Toast.LENGTH_SHORT).show();

    }

6--调用服务方法

使用服务中的代理类调用服务中的方法

    //调用服务中的方法
    public void useServiceMethods() {

        //有才调用
        if (myBinder != null) {
            myBinder.userMyServiceMethods();
            Toast.makeText(this, "调用服务中的方法", Toast.LENGTH_SHORT).show();
            Log.i("MyService", "调用服务中的方法");
            return;
        }
        Toast.makeText(this, "服务未连接", Toast.LENGTH_SHORT).show();


    }

3)activity_main布局文件的编写

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:id="@+id/main"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context=".MainActivity"
    android:orientation="vertical"
    >

    <TextView
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="服务的简单操作"

        android:textSize="20sp"
        android:textColor="#000000"
        android:gravity="center"
        android:layout_gravity="center"
        android:padding="20dp"
        android:background="#09EDA5"

        />
    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="vertical"
        android:gravity="center"
        android:background="#0D86FF"
        >
        <Button
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="启动服务"
            android:id="@+id/startService"
            android:theme="@style/Theme.Design.NoActionBar"
            />

        <Button
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="停止服务"
            android:id="@+id/stopService"
            android:theme="@style/Theme.Design.NoActionBar"

            />
        <Button
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="绑定服务"
            android:id="@+id/bindService"
            android:theme="@style/Theme.Design.NoActionBar"
            />
        <Button
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="解绑服务"
            android:id="@+id/unBindService"
            android:theme="@style/Theme.Design.NoActionBar"
            />
        <Button
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="使用服务方法"
            android:id="@+id/useServiceMethods"
            android:theme="@style/Theme.Design.NoActionBar"
            />

    </LinearLayout>

    <TextView
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:text="服务的简单操作"

        android:textSize="20sp"
        android:textColor="#000000"
        android:gravity="center"
        android:layout_gravity="center"
        android:padding="20dp"
        android:background="#E3EFEB"
        android:id="@+id/tv_show"

        />


</LinearLayout>

4)colors.xml文件

<?xml version="1.0" encoding="utf-8"?>
<resources>
    <color name="black">#FF000000</color>
    <color name="white">#FFFFFFFF</color>
    <color name="red">#FF0000</color>
    <color name="green">#00FF00</color>
    <color name="blue">#0000FF</color>
    <color name="yellow">#FFFF00</color>
    <color name="orange">#FFA500</color>
    <color name="purple">#800080</color>
    <color name="pink">#FFC0CB</color>
    <color name="brown">#A52A2A</color>
    <color name="gray">#808080</color>
</resources>

5)MainActivity代码

package com.xiji.myservice;

import android.annotation.SuppressLint;
import android.content.ComponentName;
import android.content.Intent;
import android.content.ServiceConnection;
import android.os.Bundle;
import android.os.IBinder;
import android.util.Log;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;

import androidx.activity.EdgeToEdge;
import androidx.appcompat.app.AppCompatActivity;
import androidx.core.graphics.Insets;
import androidx.core.view.ViewCompat;
import androidx.core.view.WindowInsetsCompat;

public class MainActivity extends AppCompatActivity {
    private MyService myService;

    private MyService.MyServiceProxy myBinder;

    //服务连接
    private MyServiceConnection myServiceConnection ;

    //五个控件按钮
    private Button startServiceBtn;
    private Button stopServiceBtn;
    private Button bindServiceBtn;
    private Button unBindServiceBtn;
    private Button useServiceMethodsBtn;
    //视图
    private TextView textView;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        EdgeToEdge.enable(this);
        setContentView(R.layout.activity_main);
        ViewCompat.setOnApplyWindowInsetsListener(findViewById(R.id.main), (v, insets) -> {
            Insets systemBars = insets.getInsets(WindowInsetsCompat.Type.systemBars());
            v.setPadding(systemBars.left, systemBars.top, systemBars.right, systemBars.bottom);
            return insets;
        });

        initView();
    }

    //控件初始化
    private void initView() {
        //控件初始化
        startServiceBtn = findViewById(R.id.startService);
        stopServiceBtn = findViewById(R.id.stopService);
        bindServiceBtn = findViewById(R.id.bindService);
        unBindServiceBtn = findViewById(R.id.unBindService);
        useServiceMethodsBtn = findViewById(R.id.useServiceMethods);
        textView = findViewById(R.id.tv_show);

        //控件初始化
        initListener();
    }

    //控件事件绑定
    private void initListener() {
        //启动按钮事件
        startServiceBtn.setOnClickListener(new View.OnClickListener() {
            @SuppressLint("ResourceAsColor")
            @Override
            public void onClick(View v) {
                //调用启动服务 方法
                startService();
                //修改文本
                textView.setText("服务已启动");
                //修改为绿色
                textView.setTextColor(R.color.green);
            }
        });
        //停止按钮
        stopServiceBtn.setOnClickListener(new View.OnClickListener() {
            @SuppressLint("ResourceAsColor")
            @Override
            public void onClick(View v) {
                stopService();
                textView.setText("服务已停止");
                textView.setTextColor(R.color.red);
            }
        });

        //绑定按钮
        bindServiceBtn.setOnClickListener(new View.OnClickListener() {
            @SuppressLint("ResourceAsColor")
            @Override
            public void onClick(View v) {
                bindMyService();
                textView.setText("服务已绑定");
                textView.setTextColor(R.color.orange);
            }
        });

        //解绑服务
        unBindServiceBtn.setOnClickListener(new View.OnClickListener() {
            @SuppressLint("ResourceAsColor")
            @Override
            public void onClick(View v) {
                unBindMyService();

                textView.setTextColor(R.color.pink);
                textView.setText("服务已经解绑");
            }
        });
        //调用服务中的方法

        useServiceMethodsBtn.setOnClickListener(new View.OnClickListener() {
            @SuppressLint("ResourceAsColor")
            @Override
            public void onClick(View v) {
                if (myBinder != null) {
                    useServiceMethods();
                    Toast.makeText(MainActivity.this, "调用服务中的方法", Toast.LENGTH_SHORT).show();
                    textView.setTextColor(R.color.yellow);
                    textView.setText("调用服务中的方法");
                    return;
                }
                Toast.makeText(MainActivity.this, "请先绑定服务", Toast.LENGTH_SHORT).show();

            }
        });


    }








    //启动服务
    public void startService() {
        //通过意图启动服务
        Intent intent = new Intent(this, MyService.class);

        startService(intent);
        Toast.makeText(this, "启动服务", Toast.LENGTH_SHORT).show();
        Log.i("MyService", "启动服务");


    }

    //关闭服务
    public void stopService() {
        Intent intent = new Intent(this, MyService.class);
        stopService(intent);
        Toast.makeText(this, "停止服务", Toast.LENGTH_SHORT).show();
       Log.i("MyService", "停止服务");

    }

    //绑定服务
    public void bindMyService() {
        Intent intent = new Intent(this, MyService.class);
        //没有绑定服务时才绑定服务连接
        if (myServiceConnection == null) {
            //创建服务并且绑定
            myServiceConnection = new MyServiceConnection();
            //绑定服务
            bindService(intent, myServiceConnection, BIND_AUTO_CREATE);
            Toast.makeText(this, "绑定服务", Toast.LENGTH_SHORT).show();
            Log.i("MyService", "绑定服务");
            return ;
        }
        Toast.makeText(this, "服务已经连接", Toast.LENGTH_SHORT).show();


    }

    //解绑服务
    public void unBindMyService() {

        //有服务连接时才解绑
        if (myServiceConnection != null) {
            unbindService(myServiceConnection);
            Toast.makeText(this, "解绑服务", Toast.LENGTH_SHORT).show();
            Log.i("MyService", "解绑服务");
            myServiceConnection = null;
            //服务代理重置为空,不然还能使用
            if (myBinder != null) {
                myBinder = null;
                Toast.makeText(this, "服务代理重置为空", Toast.LENGTH_SHORT).show();
            }
            return ;
        }
        Toast.makeText(this, "服务未连接", Toast.LENGTH_SHORT).show();

    }

    //调用服务中的方法
    public void useServiceMethods() {

        //有才调用
        if (myBinder != null) {
            myBinder.userMyServiceMethods();
            Toast.makeText(this, "调用服务中的方法", Toast.LENGTH_SHORT).show();
            Log.i("MyService", "调用服务中的方法");
            return;
        }
        Toast.makeText(this, "服务未连接", Toast.LENGTH_SHORT).show();


    }

    //服务连接类
    private class MyServiceConnection implements ServiceConnection {
        @Override
        public void onServiceConnected(ComponentName name, IBinder service) {
            //连接服务时为其中的方法赋值
            myBinder = (MyService.MyServiceProxy) service;

            Log.i("MyService", "onServiceConnected连接服务" + service.toString());
        }

        @Override
        public void onServiceDisconnected(ComponentName name) {

        }
    }


}

6)效果图

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值