// Needed by Galaxy S (can't switch to/from speaker while playing and still keep mic working)
// Implemented directly in msandroid.cpp (sound filters for Android).
-extern "C" void msandroid_hack_speaker_state(bool speakerOn);
-
-extern "C" void Java_org_linphone_LinphoneManager_hackSpeakerState(JNIEnv* env,jobject thiz,jboolean speakerOn){
- msandroid_hack_speaker_state(speakerOn);
+extern "C" void Java_org_linphone_core_LinphoneCoreImpl_forceSpeakerState(JNIEnv *env, jobject thiz, jlong ptr, jboolean speakerOn) {
+ LinphoneCore *lc = (LinphoneCore *)ptr;
+ LinphoneCall *call = linphone_core_get_current_call(lc);
+ if (call && call->audiostream && call->audiostream->soundread) {
+ bool_t on = speakerOn;
+ ms_filter_call_method(call->audiostream->soundread, MS_AUDIO_CAPTURE_FORCE_SPEAKER_STATE, &on);
+ }
}
// End Galaxy S hack functions
return mValue;
}
}
+
+ /**
+ * Set the context of creation of the LinphoneCore.
+ */
+ public void setContext(Object context);
+
/**
* clear all added proxy configs
*/
* @throws LinphoneCoreException
*/
public void deferCallUpdate(LinphoneCall aCall) throws LinphoneCoreException;
-
+
+ public void startRinging();
+
/**
* @return a list of LinphoneCallLog
*/
* @return true is mic is muted
*/
boolean isMicMuted();
-
+
/**
* Initiate a dtmf signal if in call
* @param number
*/
boolean isEchoCancellationEnabled();
/**
- * Get echo limiter status (another method of doing echo suppressionn, more brute force)
+ * Get echo limiter status (another method of doing echo suppression, more brute force)
* @return true if echo limiter is enabled
*/
boolean isEchoLimiterEnabled();
*/
Transports getSignalingTransportPorts();
/**
- * not implemented
+ * Activates or deactivates the speaker.
* @param value
*/
void enableSpeaker(boolean value);
/**
- * not implemented
- * @return
+ * Tells whether the speaker is activated.
+ * @return true if speaker enabled, false otherwise
*/
boolean isSpeakerEnabled();
/**
*/
package org.linphone.core;
+import static android.media.AudioManager.MODE_IN_CALL;
+import static android.media.AudioManager.MODE_RINGTONE;
+import android.content.Context;
+import android.media.AudioManager;
+
import java.io.File;
import java.io.IOException;
+import org.linphone.core.LinphoneCall.State;
+import org.linphone.mediastream.video.capture.hwconf.Hacks;
+
class LinphoneCoreImpl implements LinphoneCore {
private final LinphoneCoreListener mListener; //to make sure to keep a reference on this object
private long nativePtr = 0;
+ private Context mContext = null;
+ private AudioManager mAudioManager = null;
+ private boolean mSpeakerEnabled = false;
private native long newLinphoneCore(LinphoneCoreListener listener,String userConfig,String factoryConfig,Object userdata);
private native void iterate(long nativePtr);
private native long getDefaultProxyConfig(long nativePtr);
protected void finalize() throws Throwable {
}
-
+
+ private boolean contextInitialized() {
+ if (mContext == null) {
+ Log.e("Context of LinphoneCore has not been initialized, call setContext() after creating LinphoneCore.");
+ return false;
+ }
+ return true;
+ }
+ public void setContext(Object context) {
+ mContext = (Context)context;
+ mAudioManager = (AudioManager) mContext.getSystemService(Context.AUDIO_SERVICE);
+ }
+
public synchronized void addAuthInfo(LinphoneAuthInfo info) {
isValid();
addAuthInfo(nativePtr,((LinphoneAuthInfoImpl)info).nativePtr);
}
-
-
public synchronized LinphoneProxyConfig getDefaultProxyConfig() {
isValid();
long lNativePtr = getDefaultProxyConfig(nativePtr);
public synchronized void acceptCall(LinphoneCall aCall) {
isValid();
acceptCall(nativePtr,((LinphoneCallImpl)aCall).nativePtr);
-
}
public synchronized LinphoneCallLog[] getCallLogs() {
isValid();
public synchronized void muteMic(boolean isMuted) {
muteMic(nativePtr,isMuted);
}
+
public synchronized LinphoneAddress interpretUrl(String destination) throws LinphoneCoreException {
long lAddress = interpretUrl(nativePtr,destination);
if (lAddress != 0) {
// TODO Auto-generated method stub
}
+
+ private void applyAudioHacks() {
+ if (Hacks.needGalaxySAudioHack()) {
+ /* The microphone gain is way too high on the Galaxy S so correct it here. */
+ setMicrophoneGain(-9.0f);
+ }
+ }
+ private void setAudioModeIncallForGalaxyS() {
+ if (!contextInitialized()) return;
+ mAudioManager.setMode(MODE_IN_CALL);
+ }
+ public void routeAudioToSpeakerHelper(boolean speakerOn) {
+ if (!contextInitialized()) return;
+ if (Hacks.needGalaxySAudioHack())
+ setAudioModeIncallForGalaxyS();
+ mAudioManager.setSpeakerphoneOn(speakerOn);
+ }
+ private native void forceSpeakerState(long nativePtr, boolean speakerOn);
public void enableSpeaker(boolean value) {
- // TODO Auto-generated method stub
-
+ final LinphoneCall call = getCurrentCall();
+ mSpeakerEnabled = value;
+ applyAudioHacks();
+ if (call != null && call.getState() == State.StreamsRunning && Hacks.needGalaxySAudioHack()) {
+ Log.d("Hack to have speaker=", value, " while on call");
+ forceSpeakerState(nativePtr, value);
+ } else {
+ routeAudioToSpeakerHelper(value);
+ }
}
public boolean isSpeakerEnabled() {
- // TODO Auto-generated method stub
- return false;
+ return mSpeakerEnabled;
}
public synchronized void playDtmf(char number, int duration) {
playDtmf(nativePtr,number, duration);
throws LinphoneCoreException {
deferCallUpdate(nativePtr, getCallPtr(aCall));
}
+
+ public synchronized void startRinging() {
+ if (!contextInitialized()) return;
+ if (Hacks.needGalaxySAudioHack()) {
+ mAudioManager.setMode(MODE_RINGTONE);
+ }
+ }
private native void setVideoPolicy(long nativePtr, boolean autoInitiate, boolean autoAccept);
public synchronized void setVideoPolicy(boolean autoInitiate, boolean autoAccept) {