MediaSession, medya içeriği oynatmayı yönetmek ve harici cihazlarla entegrasyon için bir Android framework bileşenidir. Bluetooth kulaklıklar, Android Auto ve sistem medya merkezi ile etkileşim için birleşik bir arayüz sağlar. Android Developers Guide, 2026'ya göre, MediaSession kullanımdan kaldırılan RemoteControlClient'ın yerini alır ve sistemle senkronize olan oynatıcılar için zorunludur.
Ana Noktalar
MediaSession, bir uygulamanın medya etkinliğini bildirmesine ve harici kaynaklardan kontrol komutları almasına izin veren bir Android sistem bileşenidir. Kullanıcı Bluetooth kulaklıkta Oynat düğmesine bastığında, sistem bu olayı aktif MediaSession'a iletir ve uygulama Callback'i aracılığıyla yanıt verir.
Android 5.0'dan önce, bu amaçla RemoteControlClient kullanılıyordu, ancak yeterli esneklik sağlamıyordu ve Android Auto, akıllı saatler, akıllı hoparlörler gibi modern senaryoları desteklemiyordu. MediaSession, API 21'de tanıtıldı ve ses ve video oynatmalı tüm Android uygulamaları için fiili standart haline geldi.
Android Geliştirici Dokümantasyonu'na (2026) göre, bir uygulama her bağımsız oynatma kaynağı için bir MediaSession oluşturmalıdır. Herhangi bir zamanda yalnızca bir oturum aktif olabilir — yeni bir oturum, önceki oturumu otomatik olarak devre dışı bırakır.
MediaSession ile MediaBrowserService'in birleşimi, eksiksiz bir medya yönetim döngüsü sağlar: hizmet bir içerik ağacı (çalma listeleri, kataloglar) sunar ve oturum gezinme ve oynatma komutlarını kabul eder. Bu, Google tarafından müzik çalarlar, podcast'ler ve sesli kitaplar için önerilen mimaridir.
MediaBrowserService, bir bildirimle ön planda hizmet olarak çalışır ve Activity yok edilse bile uygulamanın çalışmaya devam etmesini sağlar. Bu, uygulama simge durumuna küçültüldüğünde bile oynatmaya devam etmesi gereken ses oynatıcıları için kritiktir.
Oturum iki tür etkileşimi destekler: MediaController'dan (istemci tarafı) komut alır ve PlaybackState aracılığıyla durumu yayınlar. MediaController aynı süreçte veya ayrı bir uygulamada olabilir — sistem, istekleri SessionToken aracılığıyla yönlendirir.
Kullanıcı Android ses asistanını çağırıp “Sonraki parçayı çal” dediğinde, sistem MediaBrowserService'e olan bağlantı üzerinden aktif MediaSession'ı bulur ve ACTION_SKIP_TO_NEXT komutunu gönderir. Uygulamanın Callback'i onSkipToNext() çağrısını alır ve PlaybackState'i günceller.
setPlaybackState() aracılığıyla PlaybackState'i güncellemek, bağlı tüm MediaController örneklerini anında bilgilendirir. Sistem medya merkezi, Bluetooth cihazı ve Android Auto güncellemeyi aynı anda alır — normal koşullarda gecikme 50 ms'yi geçmez.
PlaybackState, önemli durum bayraklarını içerir: isPlaying, konum, hız, mevcut eylemler (play, pause, seek, stop). Doğru şekilde doldurulmuş bir PlaybackState olmadan, sistem uygulamanın hangi komutları desteklediğini bilmez ve ilgili olayları göndermez.
Meta veriler (MediaMetadata), mevcut parça hakkındaki bilgilerle (başlık, sanatçı, albüm kapağı URI'si) durumu tamamlar. Android Auto ve giyilebilir cihazlar, ekranda bilgi görüntülemek için MediaMetadata kullanır. Google I/O 2024'e göre, doğru MediaMetadata doldurma, üçüncü taraf başlatıcılarda uygulamanın görünürlüğünü %40 artırır.
MediaSession mimarisi, her biri kendi rolüne sahip dört birbirine bağlı bileşenden oluşur. Tam sistem entegrasyonu için geliştiricinin dördünü de uygulaması gerekir.
Oturum, bir hizmetin veya Activity'nin onCreate yönteminde MediaSessionCompat(context, tag) çağrılarak oluşturulur. Oluşturulduktan sonra setFlags(FLAG_HANDLES_MEDIA_BUTTONS | FLAG_HANDLES_TRANSPORT_CONTROLS) çağrılmalıdır. onDestroy içinde, sistem kaynaklarını serbest bırakmak için release() çağrılır.
Yanlış yaşam döngüsü yönetimi, yaygın hatalardan biridir. release() çağrılmazsa, oturum sistemde kalır ve sonraki uygulama eski bir durum alabilir. Android 13+, oturum sızıntıları için Logcat uyarısı gösterir.
Temel entegrasyon, bir oturum oluşturma ve Callback uygulama ile başlar. API 14'ten 35'e kadar tüm Android sürümleri için birleşik API sağlayan AndroidX medya kitaplığından MediaSessionCompat kullanılması önerilir.
class MusicService : Service() {
private lateinit var mediaSession: MediaSessionCompat
private lateinit var stateBuilder: PlaybackStateCompat.Builder
override fun onCreate() {
super.onCreate()
mediaSession = MediaSessionCompat(this, "MusicService")
mediaSession.setFlags(
MediaSessionCompat.FLAG_HANDLES_MEDIA_BUTTONS
or MediaSessionCompat.FLAG_HANDLES_TRANSPORT_CONTROLS
)
mediaSession.setCallback(MediaSessionCallback())
updatePlaybackState(false)
}
private inner class MediaSessionCallback : MediaSessionCompat.Callback() {
override fun onPlay() {
updatePlaybackState(true)
}
override fun onPause() {
updatePlaybackState(false)
}
}
private fun updatePlaybackState(isPlaying: Boolean) {
stateBuilder = PlaybackStateCompat.Builder()
.setState(
if (isPlaying) PlaybackStateCompat.STATE_PLAYING
else PlaybackStateCompat.STATE_PAUSED,
AudioTrackCompat.CURRENT_POSITION_NOT_SET,
1.0f
)
.setActions(
PlaybackStateCompat.ACTION_PLAY
or PlaybackStateCompat.ACTION_PAUSE
or PlaybackStateCompat.ACTION_SKIP_TO_NEXT
or PlaybackStateCompat.ACTION_SKIP_TO_PREVIOUS
)
mediaSession.setPlaybackState(stateBuilder.build())
}
override fun onDestroy() {
mediaSession.release()
super.onDestroy()
}
}
Bu örnekte, MusicService etiketi ve medya düğmelerini işlemek için bayraklarla bir MediaSession oluşturulur. Callback, onPlay ve onPause'u uygular ve PlaybackState'i günceller. setActions yöntemi, sistemin kilit ekranında ve medya merkezinde görüntülediği mevcut eylemleri bildirir.
private fun setMetadata(title: String, artist: String) {
val metadata = MediaMetadataCompat.Builder()
.putString(MediaMetadataCompat.METADATA_KEY_TITLE, title)
.putString(MediaMetadataCompat.METADATA_KEY_ARTIST, artist)
.putLong(MediaMetadataCompat.METADATA_KEY_DURATION, 300000L)
.putString(MediaMetadataCompat.METADATA_KEY_ALBUM_ART_URI, albumArtUrl)
.build()
mediaSession.setMetadata(metadata)
}
Meta veriler, her parça değişiminde güncellenmelidir. Sistem, araç Bluetooth ekranlarında ve giyilebilir cihazlarda bilgi görüntülemek için METADATA_KEY_TITLE ve METADATA_KEY_ARTIST'i kullanır. Kapak resmi URI'si ayarlanmazsa, oynatıcı gri bir yer tutucu gösterir.
Bluetooth kulaklıklar, AVRCP 1.6+ profili aracılığıyla komut gönderir. Android bu komutları ACTION_MEDIA_BUTTON intent'leri olarak yayınlar ve FLAG_HANDLES_MEDIA_BUTTONS bayrağı ayarlandığında MediaSession tarafından yakalanır.
Kullanıcı Bluetooth kulaklıkta Oynat düğmesine bastığında, sistem KEYCODE_MEDIA_PLAY koduyla bir KeyEvent oluşturur ve bu, Callback'in onMediaButtonEvent yöntemine gönderilir. Callback'te onPlay() uygulanmışsa, sistem doğrudan çağırır. Kulaklık düğmesine tek basış KEYCODE_MEDIA_PLAY_PAUSE gönderir — oynatıcı durumu değiştirmelidir.
Modern Bluetooth kulaklıklar 5 düğmeye kadar sahip olabilir: ses +/-, play/pause, next, previous. Her düğme kendi KeyEvent'ini oluşturur ve Callback tarafından doğru şekilde işlenmelidir. Birçok kulaklıkta play/pause'a çift basış, genellikle sonraki parçaya (ACTION_SKIP_TO_NEXT) atlama olarak yorumlanır.
Android Uyumluluk Tanım Belgesi'ne (2026) göre, medya içeriği olan tüm uygulamalar KEYCODE_MEDIA_PLAY_PAUSE'u doğru şekilde işlemelidir. Bu gereksinimin göz ardı edilmesi, Google Play'de Müzik ve Ses kategorisinde uygulama puanının otomatik olarak düşmesine neden olur.
Android 11'den itibaren, sistem medya merkezi (Medya Kontrol Paneli), bildirim gölgesinde en fazla 5 son MediaSession oturumunu görüntüler. Kullanıcı, uygulamayı açmadan oynatıcıyı kontrol edebilir. Doğru görüntüleme için MediaBrowserService uygulanması ve PlaybackState'in doğru şekilde doldurulması gerekir.
Medya Kontrol Paneli şunları gösterir: parça başlığı, sanatçı, kapak resmi (MediaMetadata'den), kontrol düğmeleri (PlaybackState'in mevcut eylemlerinden). Uygulama, aktif oynatma sırasında her 10 saniyede en az bir kez PlaybackState'i güncellemezse, medya merkezi oturumu panelden gizler.
private fun startForegroundService() {
val notification = NotificationCompat.Builder(this, "media_channel")
.setSmallIcon(R.drawable.ic_play)
.setContentTitle("Şimdi oynatılıyor")
.setContentText(currentTrackTitle)
.setPriority(NotificationCompat.PRIORITY_LOW)
.setStyle(
androidx.media.app.NotificationCompat.MediaStyle()
.setMediaSession(mediaSession.sessionToken)
)
.build()
startForeground(1001, notification)
}
MediaStyle bildirimi, sessionToken aracılığıyla MediaSession'a bağlanır ve standart medya düğmelerini görüntüler. MediaStyle olmadan bildirim, kontrol düğmeleri olmayan normal bir uyarı olarak görünür. Android 13+, görüntüleme için açık POST_NOTIFICATIONS izni gerektirir.
Sıkça Sorulan Sorular
Teknik olarak evet, ancak herhangi bir zamanda yalnızca bir oturum aktif kabul edilir. setActive(true) çağırmadan yeni bir oturum oluşturulduğunda, önceki oturum aktif kalır. Uygulama başına bir oturum veya aktif durum değiştirmeli bağımsız ses kaynağı başına bir oturum önerilir.
MediaSession, Audio Focus'u otomatik olarak yönetmez — bu ayrı bir mekanizmadır. onPlay komutu alındığında, geliştirici AudioManager aracılığıyla bağımsız olarak AudioFocus talep etmeli ve odağı kaybettiğinde oturum aracılığıyla oynatmayı duraklatmalıdır.
FLAG_HANDLES_MEDIA_BUTTONS ve FLAG_HANDLES_TRANSPORT_CONTROLS bayraklarının ayarlandığını kontrol edin. Ayrıca oturumun aktif olduğundan emin olun (setActive(true)). Android 12+'da, medya düğmeleri yalnızca MediaSession aracılığıyla çalışır — eski registerMediaButtonEventReceiver desteklenmez.
Temel düğme işleme için — hayır. Ancak Android Auto, Wear OS ve sistem medya merkezi ile entegrasyon için MediaBrowserService gereklidir. Google, uzun süreli ses oynatmalı tüm uygulamalarda MediaBrowserService uygulanmasını önerir.
Aktif oturumları, bunların Callback'lerini ve PlaybackState'lerini görmek için adb shell dumpsys media_session komutunu kullanın. Bu araç, etiketleri, etkinlik durumu ve son bilinen durumuyla kayıtlı tüm oturumları gösterir — hata ayıklama için kullanışlı bir araçtır.
Özet
Anahtar teslim bir mobil uygulama geliştireceğiz
IT Sectr, 2017'den beri girişimler ve işletmeler için iOS ve Android uygulamaları oluşturmaktadır. Size danışmanlık yapacak ve en iyi çözümü önereceğiz.
Ayrıca okuyun