any way to detect volume key presses or volume changes with android service?

前端 未结 4 1847
忘了有多久
忘了有多久 2020-12-09 14:14

Some Android apps generate a notification when the device\'s volume changes and some lock the volume. For the life of me, I cannot find out how that\'s done. Please, can s

4条回答
  •  温柔的废话
    2020-12-09 14:38

    This is one way to do it, you could just fix to a set volume instead of changing. My goal was to adjust system volume Service.

    Also, avoid doing this only when needed.

    public class VolumeKeyController {
    
        private MediaSessionCompat mMediaSession;
        private final Context mContext;
    
        public VolumeKeyController(Context context) {
            mContext = context;
        }
    
        private void createMediaSession() {
            mMediaSession = new MediaSessionCompat(mContext, KeyUtil.log);
    
            mMediaSession.setFlags(MediaSessionCompat.FLAG_HANDLES_MEDIA_BUTTONS |
                    MediaSessionCompat.FLAG_HANDLES_TRANSPORT_CONTROLS);
            mMediaSession.setPlaybackState(new Builder()
                    .setState(PlaybackStateCompat.STATE_PLAYING, 0, 0)
                    .build());
            mMediaSession.setPlaybackToRemote(getVolumeProvider());
            mMediaSession.setActive(true);
        }
    
        private VolumeProviderCompat getVolumeProvider() {
            final AudioManager audio = mContext.getSystemService(Context.AUDIO_SERVICE);
    
            int STREAM_TYPE = AudioManager.STREAM_MUSIC;
            int currentVolume = audio.getStreamVolume(STREAM_TYPE);
            int maxVolume = audio.getStreamMaxVolume(STREAM_TYPE);
            final int VOLUME_UP = 1;
            final int VOLUME_DOWN = -1;
    
            return new VolumeProviderCompat(VolumeProviderCompat.VOLUME_CONTROL_RELATIVE, maxVolume, currentVolume) {
                @Override
                public void onAdjustVolume(int direction) {
                    // Up = 1, Down = -1, Release = 0
                    // Replace with your action, if you don't want to adjust system volume
                    if (direction == VOLUME_UP) {
                        audio.adjustStreamVolume(STREAM_TYPE,
                                AudioManager.ADJUST_RAISE, AudioManager.FLAG_REMOVE_SOUND_AND_VIBRATE);
                    }
                    else if (direction == VOLUME_DOWN) {
                        audio.adjustStreamVolume(STREAM_TYPE,
                                AudioManager.ADJUST_LOWER, AudioManager.FLAG_REMOVE_SOUND_AND_VIBRATE);
                    }
                    setCurrentVolume(audio.getStreamVolume(STREAM_TYPE));
                }
            };
        }
    
        // Call when control needed, add a call to constructor if needed immediately
        public void setActive(boolean active) {
            if (mMediaSession != null) {
                mMediaSession.setActive(active);
                return;
            }
            createMediaSession();
        }
    
        // Call from Service's onDestroy method
        public void destroy() {
            if (mMediaSession != null) {
                mMediaSession.release();
            }
        }
    }
    

提交回复
热议问题