React on media buttons on Android



  • Hi,

    I have next questions regarding my music player for (not only) Android. There are last 2 things that really bother me. The first is to run the music playback as a service but I will wait with this for Qt 5.7. The music playback works quite well in background even without it.

    The second thing is the ability to control the player using media buttons. Simply catching the media button press in QML works well but only if the application is active. But I want to react to them mainly when it runs in background.

    So I guess the solution is to implement it in Android part. I tried to follow the official Android guide.

    Then I used for testing Bogdan's example that reacts on SD card mount/unmount. I modified only two Java files. I renamed the SDCardReceiver class to RemoteControlReceiver and modified it like this:

    package com.kdab.training;
    
    import android.content.BroadcastReceiver;
    import android.content.Context;
    import android.content.Intent;
    import android.view.KeyEvent;
    import android.util.Log;
    
    public class RemoteControlReceiver extends BroadcastReceiver {
        @Override
        public void onReceive(Context context, Intent intent) {
            // call the native method when it receives a new notification
            if (Intent.ACTION_MEDIA_BUTTON.equals(intent.getAction())) {
                KeyEvent event = (KeyEvent)intent.getParcelableExtra(Intent.EXTRA_KEY_EVENT);
                if (KeyEvent.KEYCODE_MEDIA_NEXT == event.getKeyCode()) {
                    NativeFunctions.onReceiveNativeMounted();
               }
           }
           if (Intent.ACTION_MEDIA_BUTTON.equals(intent.getAction())) {
               KeyEvent event = (KeyEvent)intent.getParcelableExtra(Intent.EXTRA_KEY_EVENT);
               if (KeyEvent.KEYCODE_MEDIA_PLAY_PAUSE == event.getKeyCode()) {
                   NativeFunctions.onReceiveNativeMounted();
              }
           }
        }
    }
    

    The second file I modified is RegisterReceiverRunnable.java. It now looks like this:

    package com.kdab.training;
    
    import android.app.Activity;
    import android.content.Intent;
    import android.content.IntentFilter;
    import android.media.AudioManager;
    import android.content.Context;
    import android.content.ComponentName;
    
    public class RegisterReceiverRunnable implements Runnable
    {
        private Activity m_activity;
        public RegisterReceiverRunnable(Activity activity) {
            m_activity = activity;
        }
        // this method is called on Android Ui Thread
        @Override
        public void run() {
            IntentFilter filter = new IntentFilter();
            filter.addAction(Intent.ACTION_MEDIA_BUTTON);
    
            // this method must be called on Android Ui Thread
            m_activity.registerReceiver(new RemoteControlReceiver(), filter);
    
            Context mContext = m_activity.getApplicationContext();
            AudioManager am = (AudioManager) mContext.getSystemService(Context.AUDIO_SERVICE);
            am.registerMediaButtonEventReceiver(new ComponentName(m_activity, RemoteControlReceiver.class));
        }
    }
    

    The last change was to add the lines

    <receiver android:name=".RemoteControlReceiver">
        <intent-filter>
            <action android:name="android.intent.action.MEDIA_BUTTON" />
        </intent-filter>
    </receiver>
    

    to AndroidManifest.xml. I added it in the <activity> section although I'm not sure if it is correct.

    This code finally at least compiles but the application doesn't react on media buttons in emulator. Do you have any ideas what might be wrong?


Log in to reply
 

Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.