5

I'm having a very strange problem with my application. I have a service that shows an ImageView at all times. With an onTouchListener when the user interracts with the image to make some things happen. When the service closes the ImageView is removed from the window (at least it's supposed to).

When I'm at my settings activity (which is a Fragment), at every preference change I restart the service so that the changes take place in the service. During that restart, for some strange reason, sometimes the ImageView is not removed. And after the service starts again a new ImageView is shown on top of it. If then i close the service entirely, the "orphan" ImageView just stays on the screen and if it is touched the app crashes.

This error is random..I haven't been able to connect it to a specific setting or action from my side as a user; Even by clicking on the Enable/Disable ToggleButton a few times the error can occur.

Settings Fragment

     ToggleButton enableToggle = (ToggleButton)v.findViewById(R.id.enable_toggle);
     enableToggle.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
        @Override
        public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
            // TODO Auto-generated method stub
            prefs.edit().putBoolean("HotSpotEnabled", isChecked).commit();
            if(isChecked){
                getActivity().stopService(new Intent(getActivity(),mysService.class));
                getActivity().startService(new Intent(getActivity(),myService.class));
            }
            else{
                getActivity().stopService(new Intent(getActivity(),myService.class));
            }
        }
    });

Anytime a change in user's preferences is made I restart the service with this function

    public void restartService (){
        if(myService.isRunning){
            enabledToggle.setChecked(false);
            final Handler handler = new Handler();
            handler.postDelayed(new Runnable(){
                @Override
                public void run() {
                    // TODO Auto-generated method stub
                    enabledToggle.setChecked(true);
                }
            }, 1000);
        }

    }

(i use the toggle to restart the service instead of stopService();-startService(); because for some reason the problem is less frequent this way)

if I use this function to restart the service the error occures at EVERY SINGLE execution of restart()

public void restart(){
    getActivity().stopService(new Intent(getActivity(),mysService.class));
    final Handler handler = new Handler();
    handler.postDelayed(new Runnable(){
        @Override
        public void run() {
            // TODO Auto-generated method stub
            getActivity().startService(new Intent(getActivity(),myService.class));
        }
    }, 1000);
}

This fact alone just leaves me scratching my head....

This is my code for the Service:

public class myService extends Service {
publis static boolean isRunning;
ImageView img1;
WindowManager.LayoutParams params

@Override
    public int onStartCommand(Intent intent, int flags, int startId) {
            isRunning=true;
            img1=new ImageView(this);
            //create and set bitmap to img1
            params = new WindowManager.LayoutParams(WindowManager.LayoutParams.TYPE_PHONE,
                     WindowManager.LayoutParams.FLAG_WATCH_OUTSIDE_TOUCH| 
                     WindowManager.LayoutParams.FLAG_WATCH_OUTSIDE_TOUCH| 
                     WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE,
                     PixelFormat.TRANSLUCENT);
            //set bitmap and 
            wm.addView(img1, params);
            img1.setOnTouchListener(new View.OnTouchListener() {
                     .
                     .
                     .
            });
           return START_STICKY;
     }

 @Override
    public void onDestroy() {
        super.onDestroy();
        isRunning=false;
        try{   wm.removeView(img1);  img1 = null;   }catch(Exception e){}
    }

}

Any thoughts are welcome. Thanx in advance everyone who bothers to think for a solution

Anonymous
  • 4,470
  • 3
  • 36
  • 67

1 Answers1

0

Its because onDestroy() in Service is not guaranteed to be called. (See Situations when a Service's onDestroy() method doesn't get called?) for more on that.

I am running a similar setup as you but unfortunately I have not found out a way to detect every single time the Service is stopped.

If I dont find a better workaround I will be checking the running Services in onResume of the Activity, maybe this is something you can be inspired from too, however its not a perfect solution: how to check if service is running or not

Community
  • 1
  • 1
zoltish
  • 2,122
  • 19
  • 37