Saya sedang menulis aplikasi Android pertama saya dan mencoba untuk berkomunikasi antara layanan dan kegiatan. Saya memiliki Layanan yang akan berjalan di latar belakang dan melakukan beberapa gps dan pencatatan berdasarkan waktu. Saya akan memiliki Kegiatan yang akan digunakan untuk memulai dan menghentikan Layanan.
Jadi pertama-tama, saya harus dapat mengetahui apakah Layanan berjalan saat Kegiatan dimulai. Ada beberapa pertanyaan lain di sini tentang itu, jadi saya pikir saya bisa mengetahuinya (tapi jangan ragu untuk memberikan saran).
Masalah saya yang sebenarnya: jika Aktivitas berjalan dan Layanan dimulai, saya perlu cara agar Layanan mengirim pesan ke Aktivitas. String dan bilangan bulat sederhana pada titik ini - sebagian besar pesan status. Pesan-pesan tidak akan terjadi secara teratur, jadi saya tidak berpikir polling layanan adalah cara yang baik untuk pergi jika ada cara lain. Saya hanya ingin komunikasi ini ketika Aktivitas telah dimulai oleh pengguna - Saya tidak ingin memulai Kegiatan dari Layanan. Dengan kata lain, jika Anda memulai aktivitas dan layanan berjalan, Anda akan melihat beberapa pesan status di UI aktivitas ketika sesuatu yang menarik terjadi. Jika Anda tidak memulai Kegiatan, Anda tidak akan melihat pesan-pesan ini (mereka tidak begitu menarik).
Sepertinya saya harus dapat menentukan apakah Layanan berjalan, dan jika demikian, tambahkan Kegiatan sebagai pendengar. Kemudian hapus Aktivitas sebagai pendengar saat Aktivitas berhenti atau berhenti. Apakah itu benar-benar mungkin? Satu-satunya cara saya bisa melakukannya adalah dengan memiliki Activity mengimplementasikan Parcelable dan membangun file AIDL sehingga saya bisa meneruskannya melalui antarmuka jarak jauh Layanan. Namun itu kelihatannya berlebihan, dan saya tidak tahu bagaimana Activity seharusnya mengimplementasikan writeToParcel () / readFromParcel ().
Apakah ada cara yang lebih mudah atau lebih baik? Terima kasih atas bantuannya.
EDIT:
Bagi siapa pun yang tertarik dengan ini nanti, ada kode sampel dari Google untuk menangani ini melalui AIDL di direktori sampel: /apis/app/RemoteService.java
sumber
busy-wait
beraktifitas? Bisakah Anda jelaskan?Activity.onCreate()
?Intents
dengan mengirimkan data melaluiParcellable
pesan di antara mereka?Penanya mungkin sudah lama pindah melewati ini, tetapi kalau-kalau ada orang lain yang mencari ini ...
Ada cara lain untuk menangani ini, yang saya pikir mungkin yang paling sederhana.
Tambahkan
BroadcastReceiver
ke aktivitas Anda. Daftarkan untuk menerima beberapa maksud khususonResume
dan batalkan pendaftarannyaonPause
. Kemudian kirimkan niat itu dari layanan Anda ketika Anda ingin mengirimkan pembaruan status Anda atau apa pun yang Anda miliki.Pastikan Anda tidak akan bahagia jika beberapa aplikasi lain mendengarkan Anda
Intent
(adakah yang bisa melakukan sesuatu yang jahat?), Tetapi di luar itu, Anda seharusnya baik-baik saja.Sampel kode diminta:
Dalam layanan saya, saya punya ini:
(
RefreshTask.REFRESH_DATA_INTENT
hanya string konstan.)Dalam kegiatan mendengarkan saya, saya mendefinisikan
BroadcastReceiver
:Saya menyatakan penerima saya di bagian atas kelas:
Saya mengganti
onResume
untuk menambahkan ini:Dan saya mengganti
onPause
untuk menambahkan:Sekarang aktivitas saya mendengarkan layanan saya untuk mengatakan "Hei, perbarui sendiri." Saya bisa meneruskan data di
Intent
alih - alih memperbarui tabel database dan kemudian kembali untuk menemukan perubahan dalam aktivitas saya, tetapi karena saya ingin perubahan tetap ada, masuk akal untuk meneruskan data melalui DB.sumber
Broadcasts
fantastis dan sebagai tambahan jika Anda tidak ingin siaran Anda melampaui proses Anda sendiri maka pertimbangkan untuk menggunakanLocalBroadcast
: developer.android.com/reference/android/support/v4/content/…Gunakan
LocalBroadcastManager
untuk mendaftarkan penerima untuk mendengarkan siaran yang dikirim dari layanan lokal di dalam aplikasi Anda, referensi ada di sini:http://developer.android.com/reference/android/support/v4/content/LocalBroadcastManager.html
sumber
LocalBroadcastManager
sekarang tidak digunakan lagiLiveData
atau alat pengamat lainnya: developer.android.com/reference/androidx/localbroadcastmanager/…Saya terkejut bahwa tidak ada yang memberikan referensi ke perpustakaan Bus acara Otto
http://square.github.io/otto/
Saya telah menggunakan ini di aplikasi android saya dan berfungsi dengan lancar.
sumber
android:process=":my_service"
mereka tidak dapat berkomunikasi.Menggunakan Messenger adalah cara sederhana lain untuk berkomunikasi antara Layanan dan Aktivitas.
Dalam Aktivitas, buat Handler dengan Messenger yang sesuai. Ini akan menangani pesan dari Layanan Anda.
Messenger dapat diteruskan ke layanan dengan melampirkannya ke Pesan:
Contoh lengkap dapat ditemukan di demo API: MessengerService dan MessengerServiceActivity . Lihat contoh lengkap tentang cara kerja MyService.
sumber
myService.send(message);
seharusnyamessenger.send(message);
.Metode lain yang tidak disebutkan dalam komentar lain adalah untuk mengikat ke layanan dari aktivitas menggunakan bindService () dan mendapatkan turunan dari layanan di callback ServiceConnection. Seperti dijelaskan di sini http://developer.android.com/guide/components/bound-services.html
sumber
Anda juga dapat menggunakan
LiveData
yang berfungsi sepertiEventBus
.Kemudian tambahkan pengamat dari Anda
Activity
.Anda dapat membaca lebih banyak dari blog ini .
sumber
Cara lain bisa menggunakan pengamat dengan kelas model palsu melalui aktivitas dan layanan itu sendiri, menerapkan variasi pola MVC. Saya tidak tahu apakah ini cara terbaik untuk mencapai ini, tapi itu cara yang bekerja untuk saya. Jika Anda memerlukan beberapa contoh, minta dan saya akan mengirim sesuatu.
sumber
Metode saya:
Kelas untuk mengelola mengirim dan menerima pesan dari / ke layanan / aktivitas:
Dalam Contoh Kegiatan:
Dalam Contoh Layanan:
Kirim pesan dari Aktivitas / Layanan:
Bagaimana ini bekerja:
pada aktivitas Anda memulai atau mengikat layanan. Layanan "OnBind" metode mengembalikan Binder ke MessageManager-nya, dalam Aktivitas melalui implementasi metode antarmuka "Koneksi Layanan" "OnServiceConnected" Anda mendapatkan IBinder ini dan init Anda MessageManager menggunakannya. Setelah Kegiatan init MessageManager-nya MessageHandler mengirim dan jabat tangan ke layanan sehingga dapat mengatur pengirim "MessageHandler" ("private Messenger mMsgSender;" di MessageManager). Melakukan ini layanan tahu siapa yang mengirim pesannya.
Anda juga dapat menerapkan ini menggunakan Daftar / Antrian Messenger "pengirim" di MessageManager sehingga Anda dapat mengirim beberapa pesan ke berbagai Kegiatan / Layanan atau Anda dapat menggunakan Daftar / Antrian Messenger "penerima" di MessageManager sehingga Anda dapat menerima beberapa pesan dari berbagai Kegiatan / Layanan.
Dalam contoh "MessageManager" Anda memiliki daftar semua pesan yang diterima.
Karena Anda dapat melihat hubungan antara "Activity's Messenger" dan "Service Messenger" menggunakan instance "MessageManager" ini otomatis, hal itu dilakukan melalui metode "OnServiceConnected" dan melalui penggunaan "Handshake".
Semoga ini bisa membantu Anda :) Terima kasih banyak! Sampai jumpa: D
sumber
Untuk menindaklanjuti jawaban @MrSnowflake dengan contoh kode. Ini adalah XABBER sekarang open source
Application
kelas . TheApplication
kelas sentralisasi dan koordinasiListeners
dan ManagerInterfaces dan banyak lagi. Manajer dari segala jenis dimuat secara dinamis.Activity´s
dimulai di Xabber akan melaporkan dalam jenis apaListener
mereka. Dan ketikaService
mulai, laporkan keApplication
kelas seperti yang dimulai. Sekarang untuk mengirim pesan keActivity
semua yang harus Anda lakukan adalah membuat AndaActivity
menjadilistener
tipe yang Anda butuhkan. DiOnStart()
OnPause()
register / batalkan registrasi. MerekaService
dapat memintaApplication
kelas untuk hanyalistener
perlu berbicara dengannya dan jika ada di sana maka Kegiatan siap untuk menerima.Melewati
Application
kelas Anda akan melihat ada banyak jarahan yang terjadi kemudian.sumber
Mengikat adalah cara lain untuk berkomunikasi
Terapkan antarmuka dalam Aktivitas
Berikan implementasi untuk metode ini
Bind Aktivitas ke Layanan
Daftarkan dan Batalkan Pendaftaran Callback ketika Layanan terikat dan tidak terikat dengan Activity.
Inisialisasi panggilan balik
Meminta metode panggilan balik kapan pun diperlukan
sumber
serviceConnection
kehabisanonCreate
. Harap edit.Seperti yang disebutkan oleh Madhur, Anda dapat menggunakan bus untuk komunikasi.
Jika menggunakan Bus, Anda memiliki beberapa opsi:
Pustaka Bus acara Otto (tidak digunakan lagi untuk RxJava)
http://square.github.io/otto/
EventBus Robot Hijau
http://greenrobot.org/eventbus/
NYBus (RxBus, diimplementasikan menggunakan RxJava. Sangat mirip dengan EventBus)
https://github.com/MindorksOpenSource/NYBus
sumber
Selain LocalBroadcastManager, Event Bus dan Messenger sudah menjawab dalam pertanyaan ini, kita dapat menggunakan Pending Intent untuk berkomunikasi dari layanan.
Seperti yang disebutkan di sini di posting blog saya
sumber