【Android開發-26】Android中服務Service詳細講解

1,service的生命周期

Android中的Service,其生命周期相較Activity來說更為簡潔。它也有著自己的生命周期函數,系統會在特定的時刻調用對應的Service生命周期函數。

具體來說,Service的生命周期包含以下幾個方法:

onCreate():這個方法在Service被創建時調用,只會在整個Service的生命周期中被調用一次,可以在這里進行一些初始化操作。
onStartCommand():此方法在Service被啟動時調用。
onDestroy():當Service被銷毀時調用,用于執行清理工作。
此外,我們還可以通過一些手動調用的方法來管理Service的生命周期,例如startService()、stopService()和bindService()。當我們手動調用startService()后,系統會自動依次調用onCreate()和onStartCommand()這兩個方法;類似地,如果我們手動調用stopService(),則系統會自動調用onDestroy()方法。

需要注意的是,服務的生命周期比Activity的生命周期要簡單得多,但是密切關注如何創建和銷毀服務反而更加重要,因為服務可以在用戶未意識到的情況下運行于后臺。

2,service的啟動和銷毀

在Android中,Service的創建和銷毀可以通過以下代碼實現:

2.1創建Service:

public class MyService extends Service {@Overridepublic void onCreate() {super.onCreate();// 在這里進行初始化操作}@Overridepublic int onStartCommand(Intent intent, int flags, int startId) {// 在這里執行耗時操作return super.onStartCommand(intent, flags, startId);}@Overridepublic void onDestroy() {super.onDestroy();// 在這里進行清理工作}
}

2.2啟動Service:

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

2.3停止Service:

stopService(new Intent(this, MyService.class));

2.4綁定Service:

Intent intent = new Intent(this, MyService.class);
bindService(intent, serviceConnection, BIND_AUTO_CREATE);

2.5解綁Service:

unbindService(serviceConnection);

其中,serviceConnection是一個實現了ServiceConnection接口的對象,用于處理服務連接和斷開連接時的操作。

2.6在Android中,Service的注冊通常需要在應用程序的清單文件(AndroidManifest.xml)中進行。具體來說,你需要在該文件中添加一個元素,如下所示:

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

其中,“MyService”需要替換為你自定義的Service類名。

2.7service的啟動和停止代碼例子:
在Android中,可以通過Button來啟動和停止Service。具體實現方法如下:

在布局文件中添加一個Button控件:

<Buttonandroid:id="@+id/button_start_stop"android:layout_width="wrap_content"android:layout_height="wrap_content"android:text="Start/Stop Service" />

在Activity中獲取Button控件的引用,并為其設置點擊事件監聽器:

Button buttonStartStop = findViewById(R.id.button_start_stop);
buttonStartStop.setOnClickListener(new View.OnClickListener() {@Overridepublic void onClick(View v) {// 判斷Service是否正在運行,如果正在運行則停止,否則啟動if (isServiceRunning()) {stopService(new Intent(MainActivity.this, MyService.class));buttonStartStop.setText("Start Service");} else {startService(new Intent(MainActivity.this, MyService.class));buttonStartStop.setText("Stop Service");}}
});

其中,isServiceRunning()方法用于判斷Service是否正在運行,可以根據實際情況自行實現。例如:

private boolean isServiceRunning() {ActivityManager manager = (ActivityManager) getSystemService(Context.ACTIVITY_SERVICE);for (ActivityManager.RunningServiceInfo service : manager.getRunningServices(Integer.MAX_VALUE)) {if (MyService.class.getName().equals(service.service.getClassName())) {return true;}}return false;
}

3,使用bindservice方式和activity通訊

在Android中,使用bindService()方法可以將一個Activity與一個Service進行綁定,從而實現兩者之間的通信。下面是一個簡單的示例:

首先,創建一個Service類,繼承自Service,并實現Binder接口:

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 {private final IBinder mBinder = new LocalBinder();public class LocalBinder extends Binder {MyService getService() {return MyService.this;}}@Overridepublic IBinder onBind(Intent intent) {return mBinder;}public void performTask() {Log.d("MyService", "Performing task...");}
}

在Activity中,使用bindService()方法將Activity與Service進行綁定,并通過ServiceConnection監聽服務連接狀態:

import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.ServiceConnection;
import android.os.Bundle;
import android.os.IBinder;
import androidx.appcompat.app.AppCompatActivity;public class MainActivity extends AppCompatActivity {private MyService myService;private boolean isBound = false;private ServiceConnection connection = new ServiceConnection() {@Overridepublic void onServiceConnected(ComponentName className, IBinder service) {MyService.LocalBinder binder = (MyService.LocalBinder) service;myService = binder.getService();isBound = true;}@Overridepublic void onServiceDisconnected(ComponentName arg0) {isBound = false;}};@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);Intent intent = new Intent(this, MyService.class);bindService(intent, connection, Context.BIND_AUTO_CREATE);}@Overrideprotected void onDestroy() {super.onDestroy();if (isBound) {unbindService(connection);isBound = false;}}
}

在需要的時候,可以通過MyService實例調用performTask()方法來執行任務:

myService.performTask();

4,前臺服務

在Android中,前臺服務是一種在后臺運行的服務,但會顯示一個通知。以下是一個簡單的前臺服務的參考代碼:

首先,創建一個繼承自Service的類,并實現onCreate()和onDestroy()方法。在onCreate()方法中,調用startForeground()方法啟動前臺服務。

import android.app.Notification;
import android.app.PendingIntent;
import android.app.Service;
import android.content.Intent;
import android.os.IBinder;
import androidx.core.app.NotificationCompat;public class MyForegroundService extends Service {private static final int NOTIFICATION_ID = 1;@Overridepublic void onCreate() {super.onCreate();// 創建一個通知,用于顯示在前臺服務的通知欄Notification notification = new NotificationCompat.Builder(this, "channel_id").setContentTitle("前臺服務").setContentText("這是一個前臺服務").setSmallIcon(R.drawable.ic_notification).build();// 創建一個點擊通知后打開的IntentIntent intent = new Intent(this, MainActivity.class);PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, intent, 0);// 將點擊事件與通知關聯起來notification.setContentIntent(pendingIntent);// 啟動前臺服務,并將通知傳遞給系統startForeground(NOTIFICATION_ID, notification);}@Overridepublic void onDestroy() {super.onDestroy();// 停止前臺服務stopForeground(true);}@Overridepublic IBinder onBind(Intent intent) {return null;}
}

在AndroidManifest.xml文件中注冊前臺服務:

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

在需要的時候,可以通過以下代碼啟動前臺服務:

Intent intent = new Intent(this, MyForegroundService.class);
startService(intent);

在不需要前臺服務時,可以通過以下代碼停止前臺服務:

Intent intent = new Intent(this, MyForegroundService.class);
stopService(intent);

5,Intentservice的用法

在Android中,IntentService是一個用于處理后臺任務的類。它繼承自Service類,并實現了IntentService接口。以下是一個簡單的IntentService用法示例:

首先,創建一個繼承自IntentService的類,例如MyIntentService:

import android.app.IntentService;
import android.content.Intent;
import android.os.Bundle;
import android.util.Log;public class MyIntentService extends IntentService {private static final String TAG = "MyIntentService";public MyIntentService() {super("MyIntentService");}@Overrideprotected void onHandleIntent(Intent intent) {// 在這里處理傳入的IntentString action = intent.getAction();if (action != null) {switch (action) {case "com.example.ACTION_ONE":handleActionOne();break;case "com.example.ACTION_TWO":handleActionTwo();break;default:Log.w(TAG, "Unknown action: " + action);}}}private void handleActionOne() {// 處理動作一的邏輯}private void handleActionTwo() {// 處理動作二的邏輯}
}

在需要啟動IntentService的地方,創建一個新的Intent對象,并設置其動作和數據,然后調用startService()方法啟動服務:

import android.content.Intent;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;public class MainActivity extends AppCompatActivity {private Button startButton;@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);startButton = findViewById(R.id.start_button);startButton.setOnClickListener(new View.OnClickListener() {@Overridepublic void onClick(View v) {startMyIntentService();}});}private void startMyIntentService() {Intent intent = new Intent(this, MyIntentService.class);intent.setAction("com.example.ACTION_ONE");startService(intent);}
}

在這個示例中,當用戶點擊start_button按鈕時,會啟動一個名為MyIntentService的服務,并傳遞一個動作為com.example.ACTION_ONE的Intent。MyIntentService會根據傳入的動作執行相應的處理邏輯。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/215584.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/215584.shtml
英文地址,請注明出處:http://en.pswp.cn/news/215584.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

[筆記] 使用 qemu/grub 模擬系統啟動(單分區)

背景 最近在學習操作系統&#xff0c;需要從零開始搭建系統&#xff0c;由于教程中給的虛擬機搭建的方式感覺還是過于重量級&#xff0c;因此研究了一下通過 qemu 模擬器&#xff0c;配合 grub 完成啟動系統的搭建。 qemu 介紹 qemu 是一款十分優秀的系統模擬器&#xff0c;…

Linux上進行Nacos安裝

Nacos安裝指南 僅供參考&#xff0c;若有錯誤&#xff0c;歡迎批評指正&#xff01; 后期會繼續上傳docker安裝nacos的過程&#xff01; 1.Windows安裝 開發階段采用單機安裝即可。 1.1.下載安裝包 在Nacos的GitHub頁面&#xff0c;提供有下載鏈接&#xff0c;可以下載編譯好…

《C++新經典設計模式》之第7章 單例模式

《C新經典設計模式》之第7章 單例模式 單例模式.cpp 單例模式.cpp #include <iostream> #include <memory> #include <mutex> #include <vector> #include <atomic> using namespace std;// 懶漢式&#xff0c;未釋放 namespace ns1 {class Gam…

手動搭建koa+ts項目框架(日志篇)

文章目錄 前言一、安裝koa-logger二、引入koa-logger并使用總結如有啟發&#xff0c;可點贊收藏喲~ 前言 本文基于手動搭建koats項目框架&#xff08;路由篇&#xff09;新增日志記錄 一、安裝koa-logger npm i -S koa-onerror and npm i -D types/koa-logger二、引入koa-lo…

【每日一題】【12.11】1631.最小體力消耗路徑

&#x1f525;博客主頁&#xff1a; A_SHOWY&#x1f3a5;系列專欄&#xff1a;力扣刷題總結錄 數據結構 云計算 數字圖像處理 1631. 最小體力消耗路徑https://leetcode.cn/problems/path-with-minimum-effort/這道題目的核心思路是&#xff1a;使用了二分查找和BFS &a…

PHP基礎(2)

目錄 一、PHP 數據類型 二、PHP 字符操作函數 strlen() str_word_count() strrev() strpos() str_replace() 一、PHP 數據類型 PHP 有八種基本數據類型和兩種復合數據類型&#xff1a; 整型&#xff08;int&#xff09;&#xff1a;表示整數&#xff0c;可以是正數或負數&am…

線程Thread源代碼思想學習1

1.啟動線程代碼 public class MultiThreadExample {public static void main(String[] args) {// 創建兩個線程對象Thread thread1 new Thread(new Task());Thread thread2 new Thread(new Task());// 啟動線程thread1.start();thread2.start();} }class Task implements Ru…

EXPLAIN 執行計劃

有了慢查詢語句后&#xff0c;就要對語句進行分析。一條查詢語句在經過 MySQL 查詢優化器的各種基于成本和規則的優化會后生成一個所謂的執行計劃&#xff0c;這個執行計劃展示了接下來具體執行查詢的方式&#xff0c;比如多表連接的順序是什么&#xff0c;對于每個表采用什么訪…

記錄 DevEco 開發 HarmonyOS 應用開發問題記錄 【持續更新】

HarmonyOS 應用開發問題記錄 HarmonyOS 應用開發問題記錄一、預覽器無法成功運行?如何定位預覽器無法編譯問題? 開發遇到的問題 HarmonyOS 應用開發問題記錄 一、預覽器無法成功運行? 大家看到這個是不是很頭疼? 網上能看到許多方案,基本都是關閉一個配置 但是他們并…

InitializingBean初始化--Spring容器管理

目錄 InitializingBean--自動執行一些初始化操作spring初始化bean有兩種方式&#xff1a;1.優點2.缺點2.PostConstruct 注解2.舉例使用InitializingBean接口 和PostConstruct3.初始化交給容器管理4.與main入口函數有什么區別5.在 Spring 中&#xff0c;有兩種主要的初始化 bean…

【Java SE】帶你識別什么叫做異常!!!

&#x1f339;&#x1f339;&#x1f339;個人主頁&#x1f339;&#x1f339;&#x1f339; 【&#x1f339;&#x1f339;&#x1f339;Java SE 專欄&#x1f339;&#x1f339;&#x1f339;】 &#x1f339;&#x1f339;&#x1f339;上一篇文章&#xff1a;【Java SE】帶…

Android獲取Wifi網關

公司有這樣一個應用場景&#xff1a;有一臺球機設備&#xff0c;是Android系統的&#xff0c;它不像手機&#xff0c;它沒有觸摸屏幕&#xff0c;所以我們對球機的操作很不方便&#xff0c;于是我們搞這樣一個設置&#xff1a;點擊球機電源鍵5次分享出一個熱點&#xff0c;然后…

【JVM從入門到實戰】(一) 字節碼文件

一、什么是JVM JVM 全稱是 Java Virtual Machine&#xff0c;中文譯名 Java虛擬機。 JVM 本質上是一個運行在計算機上的程序&#xff0c;他的職責是運行Java字節碼文件。 二、JVM的功能 解釋和運行 對字節碼文件中的指令&#xff0c;實時的解釋成機器碼&#xff0c;讓計算機…

C++類模板不是一開始就創建的,而是調用時生成

類模板中的成員函數和普通類中成員函數創建時機有區別的&#xff1a; 普通類中的成員函數一開始就可以創建模板類中的成員函數調用的時候才可以創建 總結;類模板中的成員函數并不是一開始就創建的&#xff0c;再調用時才去創建 #include<iostream> using namespace st…

微信小程序:模態框(彈窗)的實現

效果 wxml <!--新增&#xff08;點擊按鈕&#xff09;--> <image classimg src"{{add}}" bindtapadd_mode></image> <!-- 彈窗 --> <view class"modal" wx:if"{{showModal}}"><view class"modal-conten…

Vue中$props、$attrs和$listeners的使用詳解

文章目錄 透傳屬性如何禁止“透傳屬性和事件”多根節點設置透傳訪問“透傳屬性和事件” $props、$attrs和$listeners的使用詳解 透傳屬性 透傳屬性和事件并沒有在子組件中用props和emits聲明透傳屬性和事件最常見的如click和class、id、style當子組件只有一個根元素時&#xf…

jOOQ指南中使用的數據庫

jOOQ指南中使用的數據庫 本指南中使用的數據庫將在本節中進行總結和創建 使用Oracle方言來創建 # 創建語言 CREATE TABLE language (id NUMBER(7) NOT NULL PRIMARY KEY,cd CHAR(2) NOT NULL,description VARCHAR2(50) );# 創建作者 CREATE TABLE author (id NUMBER(7) NOT …

mysql:需要準確存儲的帶小數的數據,要使用DECIMAL類型

需要準確存儲的帶小數的數據&#xff0c;要使用DECIMAL&#xff0c;特別是涉及金錢類的業務。而不要使用FLOAT或者DOUBLE。 因為DECIMAL是準確值&#xff0c;不會損失精度。 而FLOAT或者DOUBLE是近似值&#xff0c;會損失精度。 https://dev.mysql.com/doc/refman/8.2/en/fixe…

差生文具多系列之最好看的編程字體

&#x1f4e2;?聲明&#xff1a; &#x1f344; 大家好&#xff0c;我是風箏 &#x1f30d; 作者主頁&#xff1a;【古時的風箏CSDN主頁】。 ?? 本文目的為個人學習記錄及知識分享。如果有什么不正確、不嚴謹的地方請及時指正&#xff0c;不勝感激。 直達博主&#xff1a;「…

數據結構 | Floyd

參考博文&#xff1a; floyd算法 弗洛伊德算法 多源最短路徑算法_弗洛伊德算法例題-CSDN博客