Autore Topic: Richiamare metodo del service dopo il bind  (Letto 1101 volte)

Offline GiuseppeT

  • Nuovo arrivato
  • *
  • Post: 9
  • Respect: 0
    • Mostra profilo
  • Dispositivo Android:
    Nexus One
  • Sistema operativo:
    Windows 7, Mac OS X Lion
Richiamare metodo del service dopo il bind
« il: 29 Novembre 2011, 18:12:54 CET »
0
Ciao a tutti, sono nuovo sia del forum che della programmazione per Android. Scrivo questo post per chiedervi aiuto sui service.
Leggendo le guide di Google mi sono imbattuto su questo esempio di Bind tra Service e Activity:  http://developer.android.com/guide/topics/fundamentals/bound-services.html

Codice (Java): [Seleziona]
public class LocalService extends Service {
    // Binder given to clients
    private final IBinder mBinder = new LocalBinder();
    // Random number generator
    private final Random mGenerator = new Random();

    /**
     * Class used for the client Binder.  Because we know this service always
     * runs in the same process as its clients, we don't need to deal with IPC.
     */

    public class LocalBinder extends Binder {
        LocalService getService() {
            // Return this instance of LocalService so clients can call public methods
            return LocalService.this;
        }
    }

    @Override
    public IBinder onBind(Intent intent) {
        return mBinder;
    }

    /** method for clients */
    public int getRandomNumber() {
      return mGenerator.nextInt(100);
    }
}

Codice (Java): [Seleziona]
public class BindingActivity extends Activity {
    LocalService mService;
    boolean mBound = false;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
    }

    @Override
    protected void onStart() {
        super.onStart();
        // Bind to LocalService
        Intent intent = new Intent(this, LocalService.class);
        bindService(intent, mConnection, Context.BIND_AUTO_CREATE);
    }

    @Override
    protected void onStop() {
        super.onStop();
        // Unbind from the service
        if (mBound) {
            unbindService(mConnection);
            mBound = false;
        }
    }

    /** Called when a button is clicked (the button in the layout file attaches to
      * this method with the android:onClick attribute) */

    public void onButtonClick(View v) {
        if (mBound) {
            // Call a method from the LocalService.
            // However, if this call were something that might hang, then this request should
            // occur in a separate thread to avoid slowing down the activity performance.
            int num = mService.getRandomNumber();
            Toast.makeText(this, "number: " + num, Toast.LENGTH_SHORT).show();
        }
    }

    /** Defines callbacks for service binding, passed to bindService() */
    private ServiceConnection mConnection = new ServiceConnection() {

        @Override
        public void onServiceConnected(ComponentName className,
                IBinder service) {
            // We've bound to LocalService, cast the IBinder and get LocalService instance
            LocalBinder binder = (LocalBinder) service;
            mService = binder.getService();
            mBound = true;
        }

        @Override
        public void onServiceDisconnected(ComponentName arg0) {
            mBound = false;
        }
    };
}

L'esempio funziona bene, ma se provo a modificare il metodo onStart() dell'activity nel seguente modo:

Codice (Java): [Seleziona]
    protected void onStart() {
        super.onStart();
        // Bind to LocalService
        Intent intent = new Intent(this, LocalService.class);
        bindService(intent, mConnection, Context.BIND_AUTO_CREATE);
       
        Button b = (Button) findViewById(R.id.button1);        
        if(mBound)
                b.setText(mService.getRandomNumber());
       
    }

mi accorgo che dopo il metodo bindService() passa del tempo prima che il service sia avviato e/o il bind sia effettivo.

Le mia domanda è: come faccio a richiamare un metodo del service all'avvio di una activity?

Vi ringrazio anticipatamente per le vostre risposte.

Offline Verandi

  • Utente normale
  • ***
  • Post: 378
  • Respect: +75
    • Mostra profilo
  • Sistema operativo:
    Windows 7
Re:Richiamare metodo del service dopo il bind
« Risposta #1 il: 29 Novembre 2011, 18:46:10 CET »
+1
Ciao! Se vuoi settare il testo nel pulsante a bind avvenuto, devi spostare il codice che setta il testo del pulsante nel metodo onServiceConnected() della ServiceConnection perché il binding è asincrono e il "lifecycle" del service viene "notificato" proprio nella ServiceConnection che passi alla richiesta di bind.  ;-)
Per richiamare un metodo del service, è proprio come nel codice che hai preso dal sito:
- Nel service crei una classe che estenda IBinder e che puoi personalizzare come vuoi. In quel caso la classe si chiama LocalBinder e ha il solo metodo getService() che restituisce l'istanza del service che è in corso.
- Nell'activity crei una ServiceConnection personalizzata che passerai nel metodo bindService(). Nel metodo onServiceConnected della tua ServiceConnection ti viene passata l'istanza della classe LocalBinder che hai creato nel Service, e quindi ne richiami il metodo getService per poter poi richiamare qualsiasi metodo pubblico del service.
« Ultima modifica: 29 Novembre 2011, 18:59:01 CET da Verandi »

Offline GiuseppeT

  • Nuovo arrivato
  • *
  • Post: 9
  • Respect: 0
    • Mostra profilo
  • Dispositivo Android:
    Nexus One
  • Sistema operativo:
    Windows 7, Mac OS X Lion
Re:Richiamare metodo del service dopo il bind
« Risposta #2 il: 29 Novembre 2011, 19:01:13 CET »
0
Si, in effetti hai ragione. Grazie mille per rapidità della tua risposta.