1 package com.example.android.apis.app; 2 3 import com.example.android.apis.R; 4 import com.example.android.apis.app.LocalServiceActivities.Binding; 5 6 import android.app.Activity; 7 import android.content.ComponentName; 8 import android.content.Context; 9 import android.content.Intent; 10 import android.content.ServiceConnection; 11 import android.os.Bundle; 12 import android.os.Handler; 13 import android.os.IBinder; 14 import android.os.Message; 15 import android.os.Messenger; 16 import android.os.RemoteException; 17 import android.view.View; 18 import android.view.View.OnClickListener; 19 import android.widget.Button; 20 import android.widget.TextView; 21 import android.widget.Toast; 22 23 public class MessengerServiceActivities { 24 25 // BEGIN_INCLUDE(bind) 26 /** 27 * Example of binding and unbinding to the remote service. 28 * This demonstrates the implementation of a service which the client will 29 * bind to, interacting with it through an aidl interface. 30 * 31 * Note that this is implemented as an inner class only keep the sample 32 * all together; typically this code would appear in some separate class. 33 */ 34 public static class Binding extends Activity { 35 /** Messenger for communicating with service. */ 36 Messenger mService = null; 37 /** Flag indicating whether we have called bind on the service. */ 38 boolean mIsBound; 39 /** Some text view we are using to show state information. */ 40 TextView mCallbackText; 41 42 /** 43 * Handler of incoming messages from service. 44 */ 45 class IncomingHandler extends Handler { 46 @Override handleMessage(Message msg)47 public void handleMessage(Message msg) { 48 switch (msg.what) { 49 case MessengerService.MSG_SET_VALUE: 50 mCallbackText.setText("Received from service: " + msg.arg1); 51 break; 52 default: 53 super.handleMessage(msg); 54 } 55 } 56 } 57 58 /** 59 * Target we publish for clients to send messages to IncomingHandler. 60 */ 61 final Messenger mMessenger = new Messenger(new IncomingHandler()); 62 63 /** 64 * Class for interacting with the main interface of the service. 65 */ 66 private ServiceConnection mConnection = new ServiceConnection() { 67 public void onServiceConnected(ComponentName className, 68 IBinder service) { 69 // This is called when the connection with the service has been 70 // established, giving us the service object we can use to 71 // interact with the service. We are communicating with our 72 // service through an IDL interface, so get a client-side 73 // representation of that from the raw service object. 74 mService = new Messenger(service); 75 mCallbackText.setText("Attached."); 76 77 // We want to monitor the service for as long as we are 78 // connected to it. 79 try { 80 Message msg = Message.obtain(null, 81 MessengerService.MSG_REGISTER_CLIENT); 82 msg.replyTo = mMessenger; 83 mService.send(msg); 84 85 // Give it some value as an example. 86 msg = Message.obtain(null, 87 MessengerService.MSG_SET_VALUE, this.hashCode(), 0); 88 mService.send(msg); 89 } catch (RemoteException e) { 90 // In this case the service has crashed before we could even 91 // do anything with it; we can count on soon being 92 // disconnected (and then reconnected if it can be restarted) 93 // so there is no need to do anything here. 94 } 95 96 // As part of the sample, tell the user what happened. 97 Toast.makeText(Binding.this, R.string.remote_service_connected, 98 Toast.LENGTH_SHORT).show(); 99 } 100 101 public void onServiceDisconnected(ComponentName className) { 102 // This is called when the connection with the service has been 103 // unexpectedly disconnected -- that is, its process crashed. 104 mService = null; 105 mCallbackText.setText("Disconnected."); 106 107 // As part of the sample, tell the user what happened. 108 Toast.makeText(Binding.this, R.string.remote_service_disconnected, 109 Toast.LENGTH_SHORT).show(); 110 } 111 }; 112 doBindService()113 void doBindService() { 114 // Establish a connection with the service. We use an explicit 115 // class name because there is no reason to be able to let other 116 // applications replace our component. 117 bindService(new Intent(Binding.this, 118 MessengerService.class), mConnection, Context.BIND_AUTO_CREATE); 119 mIsBound = true; 120 mCallbackText.setText("Binding."); 121 } 122 doUnbindService()123 void doUnbindService() { 124 if (mIsBound) { 125 // If we have received the service, and hence registered with 126 // it, then now is the time to unregister. 127 if (mService != null) { 128 try { 129 Message msg = Message.obtain(null, 130 MessengerService.MSG_UNREGISTER_CLIENT); 131 msg.replyTo = mMessenger; 132 mService.send(msg); 133 } catch (RemoteException e) { 134 // There is nothing special we need to do if the service 135 // has crashed. 136 } 137 } 138 139 // Detach our existing connection. 140 unbindService(mConnection); 141 mIsBound = false; 142 mCallbackText.setText("Unbinding."); 143 } 144 } 145 // END_INCLUDE(bind) 146 147 /** 148 * Standard initialization of this activity. Set up the UI, then wait 149 * for the user to poke it before doing anything. 150 */ 151 @Override onCreate(Bundle savedInstanceState)152 protected void onCreate(Bundle savedInstanceState) { 153 super.onCreate(savedInstanceState); 154 155 setContentView(R.layout.messenger_service_binding); 156 157 // Watch for button clicks. 158 Button button = (Button)findViewById(R.id.bind); 159 button.setOnClickListener(mBindListener); 160 button = (Button)findViewById(R.id.unbind); 161 button.setOnClickListener(mUnbindListener); 162 163 mCallbackText = (TextView)findViewById(R.id.callback); 164 mCallbackText.setText("Not attached."); 165 } 166 167 private OnClickListener mBindListener = new OnClickListener() { 168 public void onClick(View v) { 169 doBindService(); 170 } 171 }; 172 173 private OnClickListener mUnbindListener = new OnClickListener() { 174 public void onClick(View v) { 175 doUnbindService(); 176 } 177 }; 178 } 179 } 180