2017-05-24 16 views
0

同様のタイトルの質問がありますが、コンストラクタで取得するContextに関するすべての質問があります。"静的フィールドにAndroidコンテキストクラスを配置しない;これはメモリリークです" - 静的なLint警告の表示

アイテムと再生\一時停止ボタンがある他のビューを持つRecyclerViewがあります。

このクラスでは、このビューで一度に1つのファイルしか再生できません。 view_1が再生されていて、view_2で再生を押すと、file_2が再生されます。

このクラスにはImageButton mPlayPauseButtonがあります。 view_1のImageButtonをpaused_stateに設定する必要があります。そして、ビュー_2のImageButtonを、再生_状態に設定します。

リント警告

staticフィールドでのAndroidのコンテキスト・クラスを置かないでください。これはメモリリークです(また、インスタント実行が中断されます)。 静的フィールドはコンテキストをリークします。

public class CommentsAudioPlayer { 

    private static MediaPlayer mPlayer; 
    private static ImageButton mPlayPauseButton; 

    private static void init(ImageButton imageButton){ 
     mPlayer = new MediaPlayer(); 
     mPlayPauseButton = imageButton; 
    } 

    public static void startPlaying(String dataSource, ImageButton imageButton) { 
     init(imageButton); 

     try { 
      mPlayer.setDataSource(dataSource); 
      mPlayer.setOnCompletionListener(new MediaPlayer.OnCompletionListener() { 
       @Override 
       public void onCompletion(MediaPlayer mp) { 
        stopPlaying(); 
       } 
      }); 
      mPlayer.setOnPreparedListener(new MediaPlayer.OnPreparedListener() { 
       @Override 
       public void onPrepared(MediaPlayer mp) { 
        mPlayer.start(); 
       } 
      }); 
      mPlayer.prepareAsync(); 
      if (mPlayPauseButton != null) mPlayPauseButton.setSelected(true); 
     } catch (Exception e) { 
      Log.e("Player", "Error trying to start playing:\n" + e.toString()); 
     } 
    } 

    public static void stopPlaying() { 
     if (mPlayPauseButton != null) 
      mPlayPauseButton.setSelected(false); 
     mPlayPauseButton = null; 

     if (mPlayer!=null) 
      mPlayer.release(); 
     mPlayer = null; 
    } 
} 

答えて

1

staticフィールド内のウィジェットを入れないでください。

のオプションがあります。

  1. は、このクラスを削除します。このロジックをすべてウィジェットに直接アクセスできるアクティビティ(またはフラグメント)に移動します。

  2. イベントバス(LocalBroadcastManager、greenrobotのEventBusなど)を使用してください。状態が変わったときに、ここにコードを掲示してください。あなたのUI(アクティビティまたはフラグメント)をバス上のメッセージに登録し、ウィジェットを更新します。

  3. CommentsAudioPlayerのインスタンスを保持していて、CommentsAudioPlayerのフィールドを非staticにしてください。

3つのうち、最初のオプションは、よりシンプルでクリーンでメモリを消費せず、実行が速くなります。

+0

ありがとう!私はEventBus(アイデア#2)を使用しましたが、RecyclerViewのビュー内で登録/登録解除する必要があるため、最も簡単なものではありませんでした。 – Inoy

0

リークを防ぐために、ビュー(mPlayPauseButton)をその機能から切り離す必要があります。これを行うには、リスナーパターンを実装します。そのコードのより簡単な方法は、ビュー参照に直接代わりにパラメータとして "リスナー"オブジェクトを渡すことができます...

関連する問題