Android:在电话呼叫期间停止小部件的MediaPlayer活动

时间:2013-07-20 14:32:59

标签: android widget telephonymanager

我已经使用了此答案Stopping & Starting music on incoming calls中提供的解决方案,但无法弄清楚如何在我的代码中实现它。这就是我做的 -

public class KameWidget extends AppWidgetProvider {
public static String ACTION_WIDGET_RECEIVER = "ActionReceiverWidget";
MediaPlayer mPlay;
Context mContext;

@Override
public void onUpdate(Context context, AppWidgetManager appWidgetManager,
        int[] appWidgetIds) {

    RemoteViews remoteViews = new RemoteViews(context.getPackageName(),
            R.layout.main);

    Intent active = new Intent(context, KameWidget.class);
    active.setAction(ACTION_WIDGET_RECEIVER);
    PendingIntent actionPendingIntent = PendingIntent.getBroadcast(context,
            0, active, 0);
    remoteViews.setOnClickPendingIntent(R.id.IBWidget, actionPendingIntent);
    appWidgetManager.updateAppWidget(appWidgetIds, remoteViews);
}

@Override
public void onReceive(Context context, Intent intent) {

    final String action = intent.getAction();
    if (AppWidgetManager.ACTION_APPWIDGET_DELETED.equals(action)) {
        final int appWidgetId = intent.getExtras().getInt(
                AppWidgetManager.EXTRA_APPWIDGET_ID,
                AppWidgetManager.INVALID_APPWIDGET_ID);
        if (appWidgetId != AppWidgetManager.INVALID_APPWIDGET_ID) {
            this.onDeleted(context, new int[] { appWidgetId });
        }
    } else {
        if (intent.getAction().equals(ACTION_WIDGET_RECEIVER)) {

            mPlay = MediaPlayer.create(context, R.raw.kamehameha);
            mPlay.start();
            PhoneStateListener phoneStateListener = new PhoneStateListener() {
                @Override
                public void onCallStateChanged(int state,
                        String incomingNumber) {
                    if (state == TelephonyManager.CALL_STATE_RINGING
                            || state == TelephonyManager.CALL_STATE_OFFHOOK) {
                        mPlay.stop();
                    }
                    super.onCallStateChanged(state, incomingNumber);
                }
            };
            TelephonyManager mgr = (TelephonyManager) mContext
                    .getSystemService(Context.TELEPHONY_SERVICE);
            if (mgr != null) {
                mgr.listen(phoneStateListener,
                        PhoneStateListener.LISTEN_CALL_STATE);
            }
        } else {
        }
        super.onReceive(context, intent);
    }
  }
}

1 个答案:

答案 0 :(得分:0)

这是我的理解:

  • 您编写了一个媒体播放器应用小部件
  • 用户按下按钮使其开始播放(某物)
  • 来电= =>声音暂停

以下是我将继续讨论的内容:

  1. 将播放音轨的服务(android.app.Service)绑定到窗口小部件上的按钮。
  2. 该服务启动实际的MediaPlayer任务。
  3. 当有来电时,任务会暂停MediaPlayer。
  4. 当通话结束时,任务可能(取决于你想要的)恢复MediaPlayer。
  5. 1)在KameWidget.onUpdate(..)中,类似于:

    Intent intentPlay = new Intent(context, YourPlaySoundService.class);
    PendingIntent piPlay = PendingIntent.getService(context, 0, intentPlay, PendingIntent.FLAG_UPDATE_CURRENT);
    RemoteViews views = new RemoteViews(context.getPackageName(), layoutId);
    views.setOnClickPendingIntent(R.id.play, piPlay);
    ...
    

    2)服务:

    public class YourPlaySoundService extends Service {
      ...
      public int onStartCommand (Intent intent, int flags, int startId) {
        // Start the Audio Task
        // Instantiate AudioTask
        AudioTask task = new AudioTask();
        // E.g. get your resource ID from the widget:
        Bundle extras = intent.getExtras();
        int resId = extras.getInt(YOUR_RESOURCE_PARAM_KEY);
        task.execute(resId);
    
        return super.onStartCommand(intent, flags, startId);
      }
    }
    

    3)音频任务:

    public class AudioTask extends AsyncTask<Integer, Void, Void> {
      private MediaPlayer mMediaPlayer;
      // Telephony-Stuff
    
      public void resume() {
        if(/* check on correct media player state */) {
          mMediaPlayer.start();
        }
      }
      public void pause() {
        if(mMediaPlayer.isPlaying()) {
          mMediaPlayer.pause();
        }
      }
      public void stop() {
        if(mMediaPlayer.isPlaying()) {
          mMediaPlayer.stop();
        }
        mMediaPlayer.release();
        mMediaPlayer = null;
      }
    
      protected Void doInBackground(Integer ... params) {
        int resId = params[0];
        // get the resources from a context (the service)
        AssetFileDescriptor afd = mResources.openRawResourceFd(resId);
        try {   
          mMediaPlayer.reset();
          mMediaPlayer.setDataSource(
              afd.getFileDescriptor(), 
              afd.getStartOffset(),
              afd.getDeclaredLength()
              );
          mMediaPlayer.setOnPreparedListener(new OnPreparedListener() {
            public void onPrepared(MediaPlayer mp) {
              mp.seekTo(0);
              mp.start();
            }
          });
          mMediaPlayer.prepare();
          afd.close();
        }
        catch (Exception e) {
          Log.e("TAG", e.getMessage(), e);
        }
        return null;
      }
    
      // Copied from your link: http://stackoverflow.com/a/5610996/747906
      PhoneStateListener phoneStateListener = new PhoneStateListener() {
        @Override
        public void onCallStateChanged(int state, String incomingNumber) {
            if (state == TelephonyManager.CALL_STATE_RINGING) {
                mMediaPlayer.pause();
            } else if(state == TelephonyManager.CALL_STATE_IDLE) {
                //Not in call: Play music
            } else if(state == TelephonyManager.CALL_STATE_OFFHOOK) {
                //A call is dialing, active or on hold
            }
            super.onCallStateChanged(state, incomingNumber);
        }
      };
    }
    

    我真的不知道电话的工作原理。你必须自己搞清楚。

    这是我的想法。我希望它有所帮助。