앱개발을 하다보면 사운드관련 처리를 하게되고, 사운드 처리를 하다보면 단말 내 타 앱과 간섭이 발생하게 된다.
뭔가 그럴듯하게 적으려하다보니 어렵게 설명이 되었는데..... 쉽게 설명하면 간단하다.
내가 만든앱에서 가령 '이 편지는 영국에서 시작되어....'라는 음성이 발성되어야한다고하면
해당 음성이 발성중일때 다른 앱에서 동일 크기에 음성이 발성된다면 개발자는 사용자에게 행운의 편지를 정상적으로 배달하는데 어려움이 발생할것이다.....
이번 포스트는 개발자가 사용자에게 행운의 편지를 성공적으로 배송하기위한 방법!
AudioFocus처리 방법에 대해 정리해보고자 한다.
벌써부터 두근거렸다면 박수감사합니다.
먼저, AudioManager 옵션에 대해 알아보자.
스트림 타입 | 설명 |
---|---|
STREAM_ALARM | 알람을 의한 오디오 스트림The audio stream for alarms |
STREAM_DTMF | DTMF 톤을 위한 오디오 스트림 |
STREAM_MUSIC | "미디어"(음악, 팟캐스트, 비디오) 재생을 오디오 스트림 |
STREAM_NOTIFICATION | 알림을 위한 오디오 스트림 |
STREAM_RING | 폰 링을 위한 오디오 스트림 |
STREAM_SYSTEM | 시스템 사운드를 위한 오디오 스트림 |
위에서 알아본 옵션중 이번 포스트에서는 미디어 관련 옵션을 이용해 처리하였다.
그럼 이제 옵션도 확인했으니, AudioFocus 처리에 대해 진행해보자.
AudioFocus처리를 위해서는 우선적으로 AudioManager 내 'OnAudioFocusChangeListener'를 이용한 Listener 구현이 필요하다.
OnAudioFocusChangeListener는 이름 그대로 오디오 포커스 변환 이벤트가 감지되었을때 해당 리스너를 통해 처리가능하다.
해당 리스너를 통해 넘어오는 케이스에대한 상세정보는 다음과 같다.
획득 | 상실 |
---|---|
AUDIOFOCUS_GAIN | AUDIOFOCUS_LOSS |
AUDIOFOCUS_GAIN_TRANSIENT | AUDIOFOCUS_LOSS_TRANSIENT |
AUDIOFOCUS_GAIN_TRANSIENT_MAY_DUCK | AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK |
포커스 변경 종류 | 적절한 행동 |
---|---|
AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK | 볼륨을 줄이거나 재생을 일시정지한다. AUDIOFOCUS_LOSS_TRANSIENT의 상태를 저장한다. 애셋을 해제하면 안된다. |
AUDIOFOCUS_LOSS_TRANSIENT | 재생을 일시정지하고 상실이 일시적이란 것의 상태를 유지한다. AUDIOFOCUS_GAIN 이벤트가 나타나면 적절히 재생을 재개할 수 있다. 에셋을 해제하면 안된다. |
AUDIOFOCUS_LOSS | 재생을 정지한다. 에셋을 해제한다. |
AUDIOFOCUS_GAIN_TRANSIENT_MAY_DUCK | 해당 플래그로 포커스 확보 시 포커스가 확보된 앱을 제외한 현재 미디어 재생중인 앱의 볼륨이 줄어든다. - 기존 재생중인 미디어의 볼륨만 줄이고 싶을 때 사용 |
AUDIOFOCUS_GAIN_TRANSIENT | 짧은 시간 포커스 확보 필요시 사용 |
AUDIOFOCUS_GAIN | 상실 이벤트 후 획득 이벤트. 애플리케이션에 의해 설정된 다른 상태가 없다면 재생을 재개한다. 예를 들어 상실 이베트 이전에 사용자가 명시적으로 일시 정지한 경우. |
음.... 이름만 보면 명확하게 와닿지 않는다.
그래서 잠시 Google Developers 를 참조하면 다음과 같이 설명하고 있다.
영속적인 오디오 포커스를 처리하고싶다면 'AUDIOFOCUS_GAIN'을 쓰세요.
단지 45초 미만의 오디오 포커스만을 원한다면 'AUDIOFOCUS_GAIN_TRASIENT'를 써보세요.
15초 이내로 오디오 포커스를 갖고오면서 배경음악을 잠시 줄이고 싶다면 'AUDIOFOCUS_GAIN_TRANSIENT_MAY_DUCK'을 써보세요. 대신 15초 이상 오디오 포커스를 잡아선 안됩니다.
필자는 센치한 밤이라 그런지 느낌이 오는듯한다. 마찬가지로 지금 이 포스트를 보고있는 여러분도 같은 느낌을 받길바라며 AudioFocus처리를 위한 리스너를 구현해보자.
/**
* AudioFocus 구현
*/
private AudioManager.OnAudioFocusChangeListener audioFocusChangeLisetner =
new AudioManager.OnAudioFocusChangeListener() {
@Override
public void onAudioFocusChange(int focusChange) {
switch (focusChange) {
case AudioManager.AUDIOFOCUS_GAIN:
// 재생중인 meida 볼륨 처리
audioManager.setStreamVolume(AudioManager.STREAM_MUSIC,
audioManager.getStreamMaxVolume(AudioManager.STREAM_MUSIC),
AudioManager.FLAG_PLAY_SOUND);
break;
case AudioManager.AUDIOFOCUS_GAIN_TRANSIENT:
// 재생중인 meida 볼륨 처리
break;
case AudioManager.AUDIOFOCUS_LOSS:
// 재생중인 meida 일시정지 처리
break;
case AudioManager.AUDIOFOCUS_LOSS_TRANSIENT:
// 재생중인 meida 일시정지 처리
break;
case AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK:
// 재생중인 meida mute 처리 또는 최소화
audioManager.setStreamVolume(AudioManager.STREAM_MUSIC, 0, AudioManager.FLAG_PLAY_SOUND);
break;
}
}
};
위에서 구현한 audioFocusChangeListener를 이용하여 Focus를 요청해보자.
Focus를 요청은 의외로 간단하다.
AudioManager 내 'requestAudioFocus'를 호출하여 요청한다.
AudioManager audioManager = (AudioManager) getContext().getSystemService(Context.AUDIO_SERVICE);
audioManager.requestAudioFocus(audioFocusChangeListner, // audioFocus 변화를 처리할 리스너
AudioManager.STREAM_MUSIC, // 포커스 요청 Audio 타입
AudioManager.AUDIOFOCUS_GAIN); // AudioFocus 요청 옵션
요청한 Focus가 정상적으로 처리되었다면, 앞서 구현한 audioFocusChangeListener를 통해 해당 이벤트가 정상전달되며, 개발자는 상황에 맞는 처리를 진행하면 된다.
AudioFocus 해제의 경우 'abandonAudioFocus' 호출을 통해 쉽게 해제할 수 있다.
AudioManager audioManager = (AudioManager) getContext().getSystemService(Context.AUDIO_SERVICE);
audioManager.abandonAudioFocus(audioFocusChangeListner);
이상 기본적인 AudioFocus 처리에 대한 포스팅을 마무리한다.
'안드로이드 > 일반' 카테고리의 다른 글
[Android] 데이터 객체전달? 이제 Parceler로 쉽게 구현하세요 (1) | 2018.04.25 |
---|---|
[Android] Json? String? 이젠 쉽게 컨버팅하자! (0) | 2018.04.15 |
[Android] Apk파일 디컴파일 방법 두가지! (2/2) (0) | 2018.02.24 |
[Android] Apk파일 디컴파일 방법 두가지! (1/2) (0) | 2018.02.24 |
[Android] 안드로이드 볼륨조절버튼 클릭시 특정 타입으로 고정하기 (0) | 2018.02.14 |