2013-04-09 41 views
9

Tôi đang viết một ứng dụng dựa trên dịch vụ với một dịch vụ bị ràng buộc và phương thức onBind() của dịch vụ dường như không bao giờ được gọi (thử nghiệm nó với Toasts và Logs).onBind() không bao giờ được gọi trong dịch vụ

Các dịch vụ:

import android.app.Notification; 
import android.app.NotificationManager; 
import android.app.PendingIntent; 
import android.app.Service; 
import android.content.Context; 
import android.content.Intent; 
import android.location.Criteria; 
import android.location.Location; 
import android.location.LocationListener; 
import android.location.LocationManager; 
import android.os.Binder; 
import android.os.Bundle; 
import android.os.IBinder; 
import android.util.Log; 
import android.widget.Toast; 
import com.gmail.zack.yovel.FlickAround.MyActivity; 
import com.gmail.zack.yovel.FlickAround.R; 
import org.json.JSONArray; 
import org.json.JSONObject; 

import java.util.ArrayList; 

/** 
* Created with IntelliJ IDEA. 
* User: Ziky 
* Date: 09/04/13 
* Time: 19:06 
* To change this template use File | Settings | File Templates. 
*/ 
public class UpdateService extends Service implements LocationListener, UpdatePhotosTask.OnHttpResponseListener { 
    private final static String API_KEY = "5255c7b02750c0fa4b15bd8ad4ec1fb7"; 
    private final static String GET_PHOTOS_FOR_LOCATION_SCHEMA = "http://api.flickr.com/services/rest/?method=flickr.photos.search&api_key=" + API_KEY + "&lat=%d&lon=%d&format=json&nojsoncallback=1"; 
    private static final String KEY_PHOTOS = "photos"; 
    private static final String KEY_PHOTO = "photo"; 
    private int NOTIFICATION = R.string.update_service_started; 
    private NotificationManager mNManager; 
    private LocationManager mLManager; 
    private String mProvider; 
    private Location mLocation; 
    private IBinder mBinder = new LocalBinder(); 
    private UpdatePhotosTask task; 

    @Override 
    public IBinder onBind(Intent intent) { 
     Toast.makeText(this, "UpdateService.onBind()", Toast.LENGTH_LONG).show(); 
     Log.i("test", "UpdateService.onBind()"); 
     mLManager.requestLocationUpdates(mProvider, 0, 1000, this); 
     return mBinder; 
    } 

    @Override 
    public void onCreate() { 
     mNManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE); 
     showNotification(); 
    } 

    @Override 
    public int onStartCommand(Intent intent, int flags, int startId) { 
     Log.i("LocalService", "Received start id " + startId + ": " + intent); 
     mLManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE); 
     Criteria criteria = new Criteria(); 
     mProvider = mLManager.getBestProvider(criteria, false); 
     mLocation = mLManager.getLastKnownLocation(mProvider); 
     return START_STICKY; 
    } 

    @Override 
    public void onDestroy() { 
     mNManager.cancel(NOTIFICATION); 
     Toast.makeText(this, R.string.update_service_stoped, Toast.LENGTH_SHORT).show(); 
    } 

    private void showNotification() { 
     CharSequence text = getText(R.string.update_service_active); 
     Notification notification = new Notification(R.drawable.refresh, text, System.currentTimeMillis()); 
     PendingIntent contentIntent = PendingIntent.getActivity(this, 0, new Intent(this, MyActivity.class), 0); 
     notification.setLatestEventInfo(this, getText(R.string.update_service_label), text, contentIntent); 
     mNManager.notify(NOTIFICATION, notification); 
    } 

    @Override 
    public void onLocationChanged(Location location) { 
     beginUpdate(location); 
    } 

    private void beginUpdate(Location location) { 
     Toast.makeText(this, "beginning update", Toast.LENGTH_LONG).show(); 
     String url = buildUrl(location); 
     task = new UpdatePhotosTask(this); 
     task.execute(url); 
    } 

    private String buildUrl(Location location) { 
     return String.format(GET_PHOTOS_FOR_LOCATION_SCHEMA, location.getLatitude(), location.getLongitude()); 
    } 

    @Override 
    public void onStatusChanged(String provider, int status, Bundle extras) { 
    } 

    @Override 
    public void onProviderEnabled(String provider) { 
    } 

    @Override 
    public void onProviderDisabled(String provider) { 
    } 

    @Override 
    public void onHttpResponse(ArrayList<String> responses) { 
     if (responses.size() > 0) { 
      String response = responses.get(0); 
      try { 
       JSONObject jsonObject = new JSONObject(response); 
       jsonObject = jsonObject.getJSONObject(KEY_PHOTOS); 
       JSONArray jsonArray = jsonObject.getJSONArray(KEY_PHOTO); 
       ArrayList<String> photos = new ArrayList<String>(); 
       for (int i = 0, length = jsonArray.length(); i < length; i++) { 
        jsonObject = jsonArray.getJSONObject(i); 
        Log.i("photo info", jsonObject.toString()); 
       } 
      } catch (Exception e) { 
       e.printStackTrace(); 
      } 
     } 
    } 

    public class LocalBinder extends Binder { 
     public UpdateService getService() { 
      return UpdateService.this; 
     } 
    } 
} 

Các AsyncTask:

import android.os.AsyncTask; 
import android.util.Log; 
import org.apache.http.HttpResponse; 
import org.apache.http.StatusLine; 
import org.apache.http.client.methods.HttpGet; 
import org.apache.http.impl.client.DefaultHttpClient; 

import java.io.BufferedReader; 
import java.io.IOException; 
import java.io.InputStream; 
import java.io.InputStreamReader; 
import java.util.ArrayList; 

/** 
* Created with IntelliJ IDEA. 
* User: Ziky 
* Date: 09/04/13 
* Time: 07:38 
* To change this template use File | Settings | File Templates. 
*/ 
public class UpdatePhotosTask extends AsyncTask<String, Void, ArrayList<String>> { 

    private OnHttpResponseListener listener; 

    public UpdatePhotosTask(OnHttpResponseListener listener) { 
     this.listener = listener; 
    } 

    @Override 
    protected ArrayList<String> doInBackground(String... urls) { 
     ArrayList<String> responses = new ArrayList<String>(); 
     for (String url : urls) { 
      StringBuilder response = new StringBuilder(); 
      DefaultHttpClient client = new DefaultHttpClient(); 
      HttpGet httpGet = new HttpGet(url); 
      try { 
       HttpResponse execute = client.execute(httpGet); 
       StatusLine statusLine = execute.getStatusLine(); 
       int statusCode = statusLine.getStatusCode(); 
       if (statusCode == 200) { 
        InputStream content = execute.getEntity().getContent(); 
        BufferedReader buffer = new BufferedReader(new InputStreamReader(content)); 
        String s = ""; 
        while ((s = buffer.readLine()) != null) { 
         response.append(s); 
        } 
        responses.add(response.toString()); 
       } else { 
        Log.e(this.getClass().toString(), "Failed to download photo list"); 
       } 
      } catch (IOException e) { 
       e.printStackTrace(); 
      } 
     } 
     return responses; 
    } 

    @Override 
    protected void onPostExecute(ArrayList<String> responses) { 
     listener.onHttpResponse(responses); 
    } 

    public interface OnHttpResponseListener { 
     public void onHttpResponse(ArrayList<String> responses); 
    } 
} 

Các hoạt động:

import android.app.Activity; 
import android.content.ComponentName; 
import android.content.Intent; 
import android.content.ServiceConnection; 
import android.os.Bundle; 
import android.os.IBinder; 
import android.os.StrictMode; 
import android.widget.Toast; 
import com.gmail.zack.yovel.FlickAround.background.UpdateService; 

public class MyActivity extends Activity { 
    private UpdateService mUpdateService; 
    private ServiceConnection mConnection = new ServiceConnection() { 
     @Override 
     public void onServiceConnected(ComponentName name, IBinder service) { 
      mUpdateService = ((UpdateService.LocalBinder) service).getService(); 
      Toast.makeText(MyActivity.this, R.string.update_service_connected, Toast.LENGTH_SHORT).show(); 
     } 

     @Override 
     public void onServiceDisconnected(ComponentName name) { 
      mUpdateService = null; 
      Toast.makeText(MyActivity.this, R.string.local_service_disconnected, Toast.LENGTH_SHORT).show(); 
     } 
    }; 
    private boolean mIsBound; 

    void doBindService() { 
     Toast.makeText(this, "MyActivity.doBindService()", Toast.LENGTH_LONG).show(); 
     bindService(new Intent(this, UpdateService.class), mConnection, BIND_AUTO_CREATE); 
     mIsBound = true; 
    } 

    void doUnbindService() { 
     if (mIsBound) { 
      unbindService(mConnection); 
      mIsBound = false; 
     } 
    } 

    @Override 
    protected void onDestroy() { 
     super.onDestroy(); 
     doUnbindService(); 
    } 

    /** 
    * Called when the activity is first created. 
    */ 
    @Override 
    public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.main); 

     // Activate StrictMode 
     StrictMode.setThreadPolicy(new StrictMode.ThreadPolicy.Builder() 
       .detectAll().penaltyLog().penaltyDeath().build()); 
     StrictMode.setVmPolicy(new StrictMode.VmPolicy.Builder().detectAll() 
       .penaltyLog().penaltyDeath().build()); 
    } 

    @Override 
    protected void onStart() { 
     super.onStart(); 
     doBindService(); 
    } 
} 

Tại sao không cho nó hoạt động?

+2

Kiểm tra LogCat cho thư, chẳng hạn như không có dịch vụ của bạn được liệt kê trong tệp kê khai. – CommonsWare

Trả lời

10

Có lẽ nguồn phổ biến nhất của ràng buộc âm thầm không có dịch vụ được liệt kê trong tệp kê khai. Điều này không làm tăng ngoại lệ, vì vậy ứng dụng của bạn không bị lỗi, nhưng sẽ có một thông báo (cảnh báo, IIRC) trong LogCat chỉ ra vấn đề của bạn.

+0

Xin cảm ơn, đây là trường hợp - Một lớp Dịch vụ khác được liệt kê trong tệp kê khai thay vì biểu mẫu này. –

Các vấn đề liên quan