Search code examples
androidandroid-asynctaskandroid-serviceandroid-mediaplayershoutcast

Android UI freeze when calling service


I developed online radio app. I called shoutcast radio server by service. When i call service all of the UI controls are freezed so that i used ProgressDialog but still freezed and didn't show progress dialog. I used AsyncTask but didn't work.

HomeFragment.java
In button onClick event, execute CallingStreamServer AsyncTask.

public class CallingStreamServer extends AsyncTask<Void, Void, Void>{

    @Override
    protected void onPreExecute() {
        // TODO Auto-generated method stub
        super.onPreExecute();
        progressDialog = new ProgressDialog(getActivity());
        progressDialog.setTitle("Please Wait");
        progressDialog.setMessage("Connecting Radio Station ...");
        progressDialog.setIndeterminate(true);
        progressDialog.setCancelable(false);
        progressDialog.show();
        //progressDialog = ProgressDialog.show(getActivity(), "Please Wait", "Connecting Radio Station ...");

    }

    @Override
    protected Void doInBackground(Void... params) {
        // TODO Auto-generated method stub          
        getActivity().startService(new Intent(getActivity(), StreamService.class));
        return null;
    }

    @Override
    protected void onPostExecute(Void result) {
        // TODO Auto-generated method stub
        progressDialog.dismiss();
        super.onPostExecute(result);
    }
}

StreamService.java
StreamService create mediaplayer and connect shoutcast radio server.

@Override
public void onCreate() {
    // TODO Auto-generated method stub
    super.onCreate();
    Log.d(TAG, "onCreate");     
    try {
        prefs = PreferenceManager.getDefaultSharedPreferences(getApplicationContext());
        sharedPreEditor = prefs.edit();

        notiManager = (NotificationManager)getApplicationContext().getSystemService(NOTIFICATION_SERVICE);
        Context context = getApplicationContext();

        String notiTitle = context.getResources().getString(R.string.app_name);
        String notiMsg = "Connecting ... ";

        Intent mainActivity = new Intent(context, MainActivity.class);
        PendingIntent pIntent = PendingIntent.getActivity(context, 0, mainActivity, 0);

        noti = new Notification.Builder(context)
                .setContentTitle(notiTitle)
                .setContentText(notiMsg)    
                .setSmallIcon(R.drawable.ic_launcher)
                .setContentIntent(pIntent)
                .build();

        notiManager.notify(notiID, noti);

        String url = prefs.getString("streamURL", "");
        mediaPlayer = new MediaPlayer();
        mediaPlayer.setAudioStreamType(AudioManager.STREAM_MUSIC);
        mediaPlayer.setDataSource(url);
        mediaPlayer.prepare();

    } catch (Exception e) {
        // TODO: handle exception
        Log.e(TAG, "onCreate Method : " + e.getMessage());          


    }
}

@Override
@Deprecated
public void onStart(Intent intent, int startId) {
    // TODO Auto-generated method stub

    super.onStart(intent, startId);
    Log.d(TAG, "onStart");

    try {

        mediaPlayer.start();
        sharedPreEditor.putBoolean("isPlaying", true);
        sharedPreEditor.commit();

        Context context = getApplicationContext();
        String notiTitle = context.getResources().getString(R.string.app_name);
        String notiMsg = prefs.getString("displayStation", "") + " radio is now playing.";

        Intent _intent = new Intent(context, MainActivity.class);
        PendingIntent pIntent = PendingIntent.getActivity(context, 0, _intent, 0);

        noti = new Notification.Builder(context)                
                .setContentTitle(notiTitle)
                .setContentText(notiMsg)
                .setSmallIcon(R.drawable.ic_launcher)   
                .setContentIntent(pIntent)              
                .build();

        noti.flags = Notification.FLAG_NO_CLEAR;

        notiManager.notify(notiID, noti);

    } catch (Exception e) {
        Log.e(TAG, "onStart Method : " + e.getMessage());
    }
}

@Override
public void onDestroy() {
    // TODO Auto-generated method stub
    Log.d(TAG, "onDestroy");
    mediaPlayer.stop();
    mediaPlayer.release();
    mediaPlayer = null;
    sharedPreEditor.putBoolean("isPlaying", false);
    sharedPreEditor.commit();       
    notiManager.cancel(notiID);
    stopSelf();
}

Solution

  • I made some of the trick for my problem. In service onCreate event, mediaPlayer.prepare() is freeze for UI that point was discern from @Doug Stevenson. So that i made 1 thread for mediaPlayer.prepare() and mediaPlayer.start() in service. I used BroadcastReceiver for service calling and results. :)

    HomeFragment.java
    Register BroadcastReceiver and button onClick event send to BroadcastReceiver for service call

    @Override
    public void onClick(View v) {
        if (v.getId() == butBoxOfMusic.getId()) {
            Intent intent = new Intent();
            intent.setAction(ACTION_STREAM_RECEIVER);
            intent.putExtra("result", "start");
            getActivity().sendBroadcast(intent);
        }
    }
    
    
    public class StreamServiceReceiver extends BroadcastReceiver{
    
        @Override
        public void onReceive(Context context, Intent intent) {
            // TODO Auto-generated method stub
    
            if (intent.getStringExtra("result").equals("start")) {
                /// Calling service(call from onClick event)
                progressDialog = ProgressDialog.show(getActivity(), "Please Wait", "Connecting Radio Station ...");
                getActivity().startService(new Intent(getActivity(), StreamService.class));
            }else{
                /// Streaming playing(result from service)
                progressDialog.dismiss();
            }
    
        }
    
    }
    

    StreamService.java
    StreamService create mediaplayer and connect shoutcast radio server.

        @Override
        public void onCreate() {
            // TODO Auto-generated method stub
            super.onCreate();
            Log.d(TAG, "onCreate");     
            try {
                prefs = PreferenceManager.getDefaultSharedPreferences(getApplicationContext());
                sharedPreEditor = prefs.edit();
    
                notiManager = (NotificationManager)getApplicationContext().getSystemService(NOTIFICATION_SERVICE);
                Context context = getApplicationContext();
    
                String notiTitle = context.getResources().getString(R.string.app_name);
                String notiMsg = "Connecting ... ";
    
                Intent mainActivity = new Intent(context, MainActivity.class);
                PendingIntent pIntent = PendingIntent.getActivity(context, 0, mainActivity, 0);
    
                noti = new Notification.Builder(context)
                        .setContentTitle(notiTitle)
                        .setContentText(notiMsg)    
                        .setSmallIcon(R.drawable.ic_launcher)
                        .setContentIntent(pIntent)
                        .build();
    
                notiManager.notify(notiID, noti);
    
                String url = prefs.getString("streamURL", "");
                mediaPlayer = new MediaPlayer();
                mediaPlayer.setAudioStreamType(AudioManager.STREAM_MUSIC);
                mediaPlayer.setDataSource(url);
    
    //          mediaPlayer.prepare();
    
            } catch (Exception e) {
                // TODO: handle exception
                Log.e(TAG, "onCreate Method : " + e.getMessage());          
    
    
            }
        }
    
        @Override
        @Deprecated
        public void onStart(Intent intent, int startId) {
            // TODO Auto-generated method stub
    
            super.onStart(intent, startId);
            Log.d(TAG, "onStart");
    
            try {
    
                Thread thread = new Thread("MediaPlayer" + String.valueOf(startId)){
                    @Override
                    public void run() {
                        // TODO Auto-generated method stub
                        super.run();
                        try {
                            mediaPlayer.prepare();
                            mediaPlayer.start();                        
    
                            sharedPreEditor.putBoolean("isPlaying", true);
                            sharedPreEditor.commit();
    
                            Context context = getApplicationContext();
                            String notiTitle = context.getResources().getString(R.string.app_name);
                            String notiMsg = prefs.getString("displayStation", "") + " radio is now playing.";
    
                            Intent _intent = new Intent(context, MainActivity.class);
                            PendingIntent pIntent = PendingIntent.getActivity(context, 0, _intent, 0);
    
                            noti = new Notification.Builder(context)                
                                    .setContentTitle(notiTitle)
                                    .setContentText(notiMsg)
                                    .setSmallIcon(R.drawable.ic_launcher)   
                                    .setContentIntent(pIntent)              
                                    .build();
    
                            noti.flags = Notification.FLAG_NO_CLEAR;
    
                            notiManager.notify(notiID, noti);
    
                            /// Send reslt to BroadcastReceiver /// 
                            Intent intent = new Intent();
                            intent.setAction(HomeFragment.ACTION_STREAM_RECEIVER);
                            intent.putExtra("result", "Playing");
                            sendBroadcast(intent);                      
    
                        } catch (IllegalStateException | IOException e) {
                            // TODO Auto-generated catch block
                            e.printStackTrace();
                        }
                    }
                };
    
                thread.start();
    
    
    
            } catch (Exception e) {
                Log.e(TAG, "onStart Method : " + e.getMessage());
            }
        }