Computer >> บทช่วยสอนคอมพิวเตอร์ >  >> การเขียนโปรแกรม >> Android

วิธีสร้าง Android Service ที่ Dalvik จะไม่ Kill


ก่อนเข้าตัวอย่าง เราควรรู้ว่า Service ใน Android คืออะไร Service จะทำ Background Operation โดยไม่โต้ตอบกับ UI และทำงานต่อแม้ Activity ถูก Destroy

ตัวอย่างนี้สาธิตวิธีสร้าง Android Service ที่ Dalvik จะไม่ Kill

Step 1 - สร้าง Project ใหม่ใน Android Studio ไปที่ File → New Project และกรอกรายละเอียดทั้งหมดเพื่อสร้าง Project ใหม่

Step 2 - เพิ่มโค้ดต่อไปนี้ใน res/layout/activity_main.xml

<?xml version = "1.0" encoding = "utf-8"?> <android.support.constraint.ConstraintLayout xmlns:android = "https://schemas.android.com/apk/res/android"    xmlns:app = "https://schemas.android.com/apk/res-auto"    xmlns:tools = "https://schemas.android.com/tools"    android:layout_width = "match_parent"    android:layout_height = "match_parent"    tools:context = ".MainActivity">    <TextView       android:id = "@+id/text"       android:layout_width = "wrap_content"       android:layout_height = "wrap_content"       android:text = "Start Service"       android:textSize = "25sp"       app:layout_constraintBottom_toBottomOf = "parent"       app:layout_constraintLeft_toLeftOf = "parent"       app:layout_constraintRight_toRightOf = "parent"       app:layout_constraintTop_toTopOf = "parent" /> </android.support.constraint.ConstraintLayout>

ในโค้ดข้างต้นเราใช้ TextView เมื่อ User คลิกที่ TextView จะ Start Service และ Stop Service

Step 3 - เพิ่มโค้ดต่อไปนี้ใน src/MainActivity.java

package com.example.andy.myapplication; import android.app.ActivityManager; import android.content.Context; import android.content.Intent; import android.support.v7.app.AppCompatActivity; import android.os.Bundle; import android.util.Log; import android.view.View; import android.widget.TextView; public class MainActivity extends AppCompatActivity {    @Override    protected void onCreate(Bundle savedInstanceState) {       super.onCreate(savedInstanceState);       setContentView(R.layout.activity_main);       final TextView text = findViewById(R.id.text);       text.setOnClickListener(new View.OnClickListener() {          @Override          public void onClick(View v) {             if (isMyServiceRunning(service.class)) {                text.setText("Stopped");                stopService(new Intent(MainActivity.this, service.class));             } else {                text.setText("Started");                startService(new Intent(MainActivity.this, service.class));             }          }       });    }    private boolean isMyServiceRunning(Class<?> serviceClass) {       ActivityManager manager = (ActivityManager) getSystemService(Context.ACTIVITY_SERVICE);       for (ActivityManager.RunningServiceInfo service : manager.getRunningServices(Integer.MAX_VALUE)) {          if (serviceClass.getName().equals(service.service.getClassName())) {             return true;          }       }       return false;    } }

ในโค้ดข้างต้นเพื่อ Start และ Stop Service เราใช้ Intent และส่ง Context และ Service Class ตอนนี้สร้าง Service Class ใน Package Folder เป็น service.class และเพิ่มโค้ดต่อไปนี้

package com.example.andy.myapplication; import android.annotation.SuppressLint; import android.annotation.TargetApi; import android.app.Notification; import android.app.NotificationChannel; import android.app.NotificationManager; import android.app.PendingIntent; import android.app.Service; import android.content.Context; import android.content.Intent; import android.graphics.Color; import android.media.MediaPlayer; import android.os.Build; import android.os.IBinder; import android.os.PowerManager; import android.support.annotation.RequiresApi; import android.support.v4.app.NotificationCompat; import android.util.Log; import android.widget.Toast; public class service extends Service {    PowerManager pm;    @SuppressLint("InvalidWakeLockTag")    PowerManager.WakeLock wl;    @Override    public IBinder onBind(Intent intent) {       return null;    }    @SuppressLint("InvalidWakeLockTag")    @Override    public void onCreate() {       super.onCreate();       pm = (PowerManager) getSystemService(Context.POWER_SERVICE);       wl = pm.newWakeLock(PowerManager.SCREEN_DIM_WAKE_LOCK, "My Tag");    }    @TargetApi(Build.VERSION_CODES.O)    @RequiresApi(api = Build.VERSION_CODES.JELLY_BEAN)    @Override    public int onStartCommand(Intent intent, int flags, int startId) {       wl.acquire();       //Do some task       Toast.makeText(this, "Notification Service started by user.", Toast.LENGTH_LONG).show();       return START_STICKY;    }    @RequiresApi(api = Build.VERSION_CODES.N)    @Override    public void onDestroy() {       super.onDestroy();       wl.release();       Toast.makeText(this, "Notification Service destroyed by user.", Toast.LENGTH_LONG).show();    } }

ในโค้ดข้างต้นเราเรียก Power Manager เพื่อป้องกัน Screen Lock ดังนั้น Android Thread จะไม่หยุด Service Thread ดังนี้

@SuppressLint("InvalidWakeLockTag") @Override public void onCreate() {    super.onCreate();    pm = (PowerManager) getSystemService(Context.POWER_SERVICE);    wl = pm.newWakeLock(PowerManager.SCREEN_DIM_WAKE_LOCK, "My Tag"); } @TargetApi(Build.VERSION_CODES.O) @RequiresApi(api = Build.VERSION_CODES.JELLY_BEAN) @Override public int onStartCommand(Intent intent, int flags, int startId) {    wl.acquire();    //Do some task    Toast.makeText(this, "Notification Service started by user.", Toast.LENGTH_LONG).show();    return START_STICKY; } @RequiresApi(api = Build.VERSION_CODES.N) @Override public void onDestroy() {    super.onDestroy();    wl.release();    Toast.makeText(this, "Notification Service destroyed by user.", Toast.LENGTH_LONG).show(); }

Step 4 - เพิ่มโค้ดต่อไปนี้ใน manifest.xml

<?xml version = "1.0" encoding = "utf-8"?> <manifest xmlns:android = "https://schemas.android.com/apk/res/android"    package = "com.example.andy.myapplication">    <uses-permission android:name = "android.permission.WAKE_LOCK"/>    <application       android:allowBackup = "true"       android:icon = "@mipmap/ic_launcher"       android:label = "@string/app_name"       android:roundIcon = "@mipmap/ic_launcher_round"       android:supportsRtl = "true"       android:theme = "@style/AppTheme">       <activity android:name = ".MainActivity">          <intent-filter>             <action android:name = "android.intent.action.MAIN" />             <category android:name = "android.intent.category.LAUNCHER" />          </intent-filter>       </activity>       <service android:name = ".service"/> </application> </manifest>

ลองรันแอปพลิเคชันของคุณ สมมติว่าคุณเชื่อม Android Device จริงกับคอมพิวเตอร์แล้ว เพื่อรันแอปจาก Android Studio ให้เปิดไฟล์ Activity ของโปรเจกต์และคลิกไอคอน Run จาก Toolbar เลือก Mobile Device ของคุณเป็นตัวเลือก และตรวจสอบ Mobile Device ซึ่งจะแสดงหน้าจอ Default

วิธีสร้าง Android Service ที่ Dalvik จะไม่ Kill

ในผลลัพธ์ข้างต้นเป็นหน้าจอเริ่มต้น คลิกที่ TextView จะเริ่ม Notification Service ดังนี้

วิธีสร้าง Android Service ที่ Dalvik จะไม่ Kill

ในผลลัพธ์ข้างต้น Service เริ่มต้นแล้ว ตอนนี้คลิกที่ TextView จะหยุด Notification Service ดังนี้

วิธีสร้าง Android Service ที่ Dalvik จะไม่ Kill